block_class_styles.module in Block Class Styles 7.2
Same filename and directory in other branches
Base module file for block_class_styles
block_class_styles Block Class Presets
File
block_class_styles.moduleView source
<?php
/**
* @file
* Base module file for block_class_styles
*
* @defgroup block_class_styles Block Class Presets
* @{
*/
/**
* @var BLOCK_CLASS_STYLES_PATH_SETTINGS
*
* Path to the settings page
*/
define('BLOCK_CLASS_STYLES_PATH_SETTINGS', 'admin/structure/block/styles');
/**
* @var BLOCK_CLASS_STYLES_ENTITY_SETTING_URL
*
* This is the path that will be used to toggle a bundle's support
*/
define('BLOCK_CLASS_STYLES_ENTITY_SETTING_URL', 'block-class-styles/setting');
/**
* @var BLOCK_CLASS_STYLES_TITLE_FORMAT
*
* Default format for titles, leave NULL to use drupal core sanitization
*/
define('BLOCK_CLASS_STYLES_TITLE_FORMAT', NULL);
/**
* @var BLOCK_CLASS_STYLES_HIDE_CLASSES
*
* Default value for hiding the block_class textfield
*/
define('BLOCK_CLASS_STYLES_HIDE_CLASSES', TRUE);
/**
* @var BLOCK_CLASS_STYLES_FS_TITLE
*
* Default fieldset title
*/
define('BLOCK_CLASS_STYLES_FS_TITLE', 'Theme/Style');
/**
* @var BLOCK_CLASS_STYLES_FS_DESCRIPTION
*
* Default fieldset description
*/
define('BLOCK_CLASS_STYLES_FS_DESCRIPTION', 'Control the appearance of this block by choosing a style for it.');
/**
* @var BLOCK_CLASS_STYLES_DESCRIPTION
*
* The default description that appears under the select element
*/
define('BLOCK_CLASS_STYLES_DESCRIPTION', '');
/**
* @var BLOCK_CLASS_STYLES_TITLE
*
* The default select title
*/
define('BLOCK_CLASS_STYLES_TITLE', 'Block Style');
/**
* @var BLOCK_CLASS_STYLES_ALLOW_MULTIPLE
*
* True/False Should we allow more than one class?
*/
define('BLOCK_CLASS_STYLES_ALLOW_MULTIPLE', FALSE);
/**
* Implements hook_help().
*
* http://api.drupal.org/api/function/hook_help
*
* @param string $path
* The router menu path, as defined in hook_menu(), for the help that is
* being requested; e.g., 'admin/node' or 'user/edit'. If the router path
* includes a % wildcard, then this will appear in $path; for example, node
* pages would have $path equal to 'node/%' or 'node/%/view'. Your hook
* implementation may also be called with special descriptors after a "#"
* sign.
* @param array $arg
* An array that corresponds to the return value of the arg() function, for
* modules that want to provide help that is specific to certain values of
* wildcards in $path. For example, you could provide help for the path
* 'user/1' by looking for the path 'user/%' and $arg[1] == '1'. This array
* should always be used rather than directly invoking arg(), because your
* hook implementation may be called for other purposes besides building the
* current page's help. Note that depending on which module is invoking
* hook_help, $arg may contain only empty strings. Regardless, $arg[0] to
* $arg[11] will always be set.
*/
function block_class_styles_help($path, $arg) {
$output = '';
if ($path === BLOCK_CLASS_STYLES_PATH_SETTINGS) {
$output .= <<<EOD
<p>Use this page to edit the block styles.</p>
<p>When you edit the css for a style definition and save this form, all blocks with that style will receive the new css. <strong>When editing <em>Style definitions</em> you may change the style name <em>OR</em> the css for the style, per form submission. To change both css and style name of a single Style definition, you need to do the css first, save the form, then do the style name and save the form.</strong></p>
<p>Each style generates a <a href="http://drupal.org/node/1089656" onclick="window.open(this.href); return false;">theme hook suggestion</a>, so you can override <code>block.tpl.php</code> for each style with the appropriate tpl file. See <em>Template suggestions list</em> for the template filenames that correspond to each style. This list will only appear after you have created one or more styles and saved this form.</p>
<p>Other things to note:</p>
<ul>
<li>The list of style definitions is defined by all the block classes/styles that have been previously assigned to blocks as well as any definitions made here that have not yet been assigned.</li>
<li>The only way to make all <em>Style definitions</em> disappear (from the box below) is to remove all classes/styles from each and every block.</li>
<li>However, you may hide a style from appearing in the styles list on block edit forms by unchecking it from the select list options below.</li>
<li><strong>Unchecking a style from the select list options does not affect a block with that style assigned to it.</strong> To affect the block you need to edit the block itself and unassign the style.</li>
<li>An unchecked style will still appear on a block's edit form if it has been selected for that block. The style name will be appended with "***" to designate it's been hidden.</li>
</ul>
EOD;
}
return $output;
}
/**
* Implements hook_permission().
*/
function block_class_styles_permission() {
return array(
'administer block_class_styles' => array(
'title' => t('Administer Block Styles'),
'description' => t('Define styles and other settings for the module.'),
'restrict access' => TRUE,
),
'block_class_styles:use' => array(
'title' => t('Use Block Styles'),
'description' => t("See/change a given block's style when editing it."),
),
);
}
/**
* Implements hook_menu().
*/
function block_class_styles_menu() {
$items = array();
$items[BLOCK_CLASS_STYLES_PATH_SETTINGS] = array(
'title' => 'Block styles',
'description' => 'Define preset classes and styles.',
'page callback' => 'drupal_get_form',
'page arguments' => array(
'block_class_styles_admin_settings',
),
'file' => 'block_class_styles.admin.inc',
'access arguments' => array(
'administer block_class_styles',
),
'type' => MENU_LOCAL_TASK,
'weight' => 50,
);
$items[BLOCK_CLASS_STYLES_ENTITY_SETTING_URL] = array(
'title' => 'Update setting',
'page callback' => '_block_class_styles_update_entity_setting',
'access arguments' => array(
'administer block_class_styles',
),
'type' => MENU_CALLBACK,
'file' => 'block_class_styles.admin.inc',
);
return $items;
}
/**
* Returns an array of css classes for a given style name.
*
* @param $style The human readable declaration of a style.
*
* @return null|array
*/
function block_class_styles_get_css_by_style($style) {
$info = block_class_styles_info();
$classes = array_search($style, $info);
return empty($classes) ? NULL : explode(' ', $classes);
}
/**
* Return an array of style presets
*
* @param boolean $include_hidden Include hiden styles
*
* @return array Keys are classes, values are styles
*/
function block_class_styles_info($include_hidden = FALSE) {
static $drupal_static_fast;
if (!isset($drupal_static_fast)) {
$drupal_static_fast['presets'] =& drupal_static(__FUNCTION__, NULL);
}
$presets =& $drupal_static_fast['presets'];
if (!isset($presets)) {
$presets = array();
// Load distinct classes and groupings of classes from blocks table; this
// makes sure that we have a style for every class or class group that is
// currently assigned to a block.
$classes = db_select(_block_class_tablename(), 'b')
->fields('b', array(
'css_class',
))
->condition('css_class', '', '!=')
->distinct()
->execute()
->fetchCol();
foreach ($classes as $class) {
$presets[$class] = ucwords(preg_replace('/[_-]/', ' ', $class));
}
// Now match to our presets if possible; this will overwrite the automatic
// naming convention from above and add any styles that have been defined
// but not yet assigned.
$presets = variable_get('block_class_styles_presets', array()) + $presets;
// Remove any hidden styles if asked.
$hidden = variable_get('block_class_styles_hidden', array());
if (!$include_hidden) {
$presets = array_diff_key($presets, $hidden);
}
// Let other modules alter this list
drupal_alter('block_class_styles_info', $presets);
$presets = (array) $presets;
}
return $presets;
}
/**
* Implements hook_flush_caches().
*
* Scans theme info files for presets and modifies our variable
*/
function block_class_styles_flush_caches() {
$presets = variable_get('block_class_styles_presets', array());
// Scan the theme info files
$include_from_themes = array();
$info = array();
foreach (list_themes() as $name => $data) {
// Check for the parent themes because we'll need to include that info
if ($data->status && isset($data->base_themes)) {
$include_from_themes += $data->base_themes;
}
if (isset($data->info['block_class_styles'])) {
$include_from_themes[$name] = $data->info['name'];
$info[$name] = $data->info['block_class_styles'];
}
}
$info = array_intersect_key($info, $include_from_themes);
foreach ($info as $array) {
$presets = array_merge($presets, $array);
}
variable_set('block_class_styles_presets', $presets);
}
/**
* Return a style by it's css
*
* @param string $css
*
* @return string or FALSE
*/
function block_class_styles_get_style($css) {
$presets = block_class_styles_info();
return $css && array_key_exists($css, $presets) ? $presets[$css] : FALSE;
}
/**
* Return the name of the table to use based on module version
*
* @return string The name of the table.
*/
function _block_class_tablename() {
return db_field_exists('block', 'css_class') ? 'block' : 'block_class';
}
/**
* Implements hook_form_alter().
*/
function block_class_styles_form_alter(&$form, $form_state, $form_id) {
$stored_css_class = '';
if ($form_id === 'bean_form') {
$bean = $form['#entity'];
$pform = $form;
$pform['module'] = array(
'#value' => 'bean',
);
$pform['delta'] = array(
'#value' => $bean->delta,
);
$pform_id = 'block_admin_configure';
block_class_form_alter($pform, $form_state, $pform_id);
$stored_css_class = $pform['settings']['css_class']['#default_value'];
}
if (in_array($form_id, array(
'block_admin_configure',
'block_add_block_form',
))) {
//// $block->module = $form['module']['#value'];
//// $block->delta = $form['delta']['#value'];
if (!empty($form['settings']['css_class']['#default_value'])) {
$stored_css_class = $form['settings']['css_class']['#default_value'];
}
}
//
//
// Generate the form element to be shared in different forms.
if (in_array($form_id, array(
'block_admin_configure',
'block_add_block_form',
'bean_form',
))) {
$multiple = FALSE;
//@todo See admin.inc for explanation
//$multiple = current(variable_get('block_class_styles_allow_multiple', BLOCK_CLASS_STYLES_ALLOW_MULTIPLE));
$options = block_class_styles_info();
$default = array(
$stored_css_class,
);
// If the default is hidden we need to grab it
if ($stored_css_class && !array_key_exists($stored_css_class, $options)) {
// $default_is_hidden = TRUE;
$hidden = block_class_styles_info(TRUE);
$options += array_intersect_key($hidden, array_flip($default));
$options[$stored_css_class] .= ' ***';
}
if (!$multiple) {
$options = array(
NULL => t('-None-'),
) + $options;
$default = $stored_css_class;
}
$element = array(
'#type' => 'fieldset',
'#title' => variable_get('block_class_styles_fs_title', BLOCK_CLASS_STYLES_FS_TITLE),
'#description' => variable_get('block_class_styles_fs_description', BLOCK_CLASS_STYLES_FS_DESCRIPTION),
'#collapsible' => TRUE,
'#collapsed' => !variable_get('block_class_styles_form_collapsed', FALSE),
);
$element['css_class'] = array(
'#type' => $multiple ? 'checkboxes' : 'select',
'#title' => variable_get('block_class_styles_title', BLOCK_CLASS_STYLES_TITLE),
'#options' => $options,
'#default_value' => $default,
'#description' => variable_get('block_class_styles_description', BLOCK_CLASS_STYLES_DESCRIPTION),
'#maxlength' => 255,
);
$element['admin'] = array(
'#markup' => t('To edit styles <a href="!url">click here</a>.', array(
'!url' => url(BLOCK_CLASS_STYLES_PATH_SETTINGS, array(
'query' => drupal_get_destination(),
)),
)),
'#access' => user_access('administer block_class_styles'),
);
}
//
//
// Support for normal blocks
if (in_array($form_id, array(
'block_admin_configure',
'block_add_block_form',
))) {
$form['block_class']['#access'] = user_access('block_class_styles:use');
$form['block_class']['#title'] = variable_get('block_class_styles_fs_title', BLOCK_CLASS_STYLES_FS_TITLE);
$form['block_class']['#description'] = variable_get('block_class_styles_fs_description', BLOCK_CLASS_STYLES_FS_DESCRIPTION);
$element['#access'] = $form['block_class']['#access'];
$element['#weight'] = variable_get('block_class_styles_form_weight', 0);
$form['block_class_styles'] = $element;
// This field needs to be hidden because we show it in our own way in our
// fieldset, and... we can't set #access to FALSE because our variable name
// is the same, so we have turn it into a non-displaying type = 'value'
$form['settings']['css_class']['#type'] = 'value';
}
elseif ($form_id === 'bean_form') {
$form['block_class_styles_css_class'] = $element;
$form['#submit'][] = '_block_class_styles_form_submit';
}
}
/**
* Form submission handler
*/
function _block_class_styles_form_submit($form, &$form_state) {
// We create a pseudo form situation and leverage block_class submitter.
$pform = $form;
$pform['settings']['css_class']['#default_value'] = $form['block_class_styles_css_class']['css_class']['#default_value'];
$pform_state = $form_state;
$pform_state['values']['form_id'] = 'block_admin_configure';
$pform_state['values']['module'] = 'bean';
$pform_state['values']['delta'] = $form_state['values']['bean']->delta;
block_class_form_submit($pform, $pform_state);
}
/**
* Implements hook_block_view().
*/
function block_class_styles_block_view_alter(&$data, $block) {
if (empty($block->css_class)) {
return;
}
$name = preg_replace('/[ -]/', '_', strtolower($block->css_class));
$name = preg_replace('/[^a-z0-1_]/', '', $name);
$data['block_class_styles'] = (object) array(
'name' => $name,
'css' => drupal_html_class($name),
'title' => block_class_styles_get_style($block->css_class),
'classes_array' => array(
explode(' ', $block->css_class),
),
);
}
/**
* Implements hook_preprocess_block().
*
* @param &$vars
*
* @return NULL
*/
function block_class_styles_preprocess_block(&$vars) {
if (isset($vars['block']->css_class) && ($css = $vars['block']->css_class) && ($style = block_class_styles_get_style($css)) && ($suggestions = _block_class_styles_theme_hook_suggestion($style))) {
if ($insert_after = array_search('block__block', $vars['theme_hook_suggestions'])) {
array_splice($vars['theme_hook_suggestions'], $insert_after + 1, 0, $suggestions);
}
else {
$vars['theme_hook_suggestions'] = array_merge($vars['theme_hook_suggestions'], $suggestions);
}
}
if ($vars['block']->title && $vars['block']->title != '<none>' && ($format = variable_get('block_class_styles_title_format', BLOCK_CLASS_STYLES_TITLE_FORMAT))) {
$vars['block']->subject = check_markup($vars['block']->title, $format);
// Now strip the outermost <p> which could show up from check_markup
preg_match('/^\\s*<p>(.*)<\\/p>\\s*$/is', $vars['block']->subject, $found);
$vars['block']->subject = isset($found[1]) ? $found[1] : $vars['block']->subject;
}
}
/**
* Return the theme_hook_suggestion for a style
*
* @param string $style
*
* @return string
*/
function _block_class_styles_theme_hook_suggestion($style) {
static $drupal_static_fast;
if (!isset($drupal_static_fast)) {
$drupal_static_fast['hooks'] =& drupal_static(__FUNCTION__, NULL);
}
$hooks =& $drupal_static_fast['hooks'];
if (!isset($hooks[$style])) {
$suggestions = array();
$suggestions[] = 'block__' . strtolower(str_replace('-', '_', drupal_clean_css_identifier($style)));
if ($classes = block_class_styles_get_css_by_style($style)) {
do {
$hook = implode('__', $classes);
$suggestions[] = 'block__' . strtolower(str_replace('-', '_', drupal_html_class($hook)));
} while (array_pop($classes) && $classes);
}
$hooks[$style] = array_unique($suggestions);
}
return $hooks[$style];
}
//function block_class_menu_contextual_links_alter(&$links, $router_item, $root_path) {
// if ($root_path === 'admin/structure/block/manage/%/%') {
// $presets = block_class_styles_info();
// foreach ($presets as $key => $preset) {
// $links[] = array(
// 'title' => check_plain($preset),
// 'href' => "block_class_styles/$key",
// 'localized_options' => array(
// 'query' => drupal_get_destination() + array(
// 'token' => drupal_get_token('block_class'),
// ),
// ),
// );
// }
// }
//
// $links = $links;
//}
/**
* Implements hook_field_extra_fields().
*/
function block_class_styles_field_extra_fields() {
if (module_exists('bean') && ($bundles = _block_class_styles_bean_bundles())) {
foreach ($bundles as $bundle_type) {
$extra['bean'][$bundle_type]['form'] = array(
'block_class_styles_css_class' => array(
'weight' => 0,
'label' => variable_get('block_class_styles_title', BLOCK_CLASS_STYLES_TITLE),
'description' => variable_get('block_class_styles_description', BLOCK_CLASS_STYLES_DESCRIPTION),
'edit' => l('edit', BLOCK_CLASS_STYLES_PATH_SETTINGS, array(
'query' => drupal_get_destination(),
)),
'delete' => l('delete', BLOCK_CLASS_STYLES_ENTITY_SETTING_URL . "/bean/{$bundle_type}/0", array(
'query' => drupal_get_destination(),
)),
),
);
}
}
return $extra;
}
/**
* @return array Values are the bundle types that should include styles.
*/
function _block_class_styles_bean_bundles() {
$bundles = variable_get('block_class_styles_beans', NULL);
if (is_null($bundles)) {
$info = entity_get_info('bean');
$bundles = array_keys($info['bundles']);
}
return $bundles;
}
Functions
Name![]() |
Description |
---|---|
block_class_styles_block_view_alter | Implements hook_block_view(). |
block_class_styles_field_extra_fields | Implements hook_field_extra_fields(). |
block_class_styles_flush_caches | Implements hook_flush_caches(). |
block_class_styles_form_alter | Implements hook_form_alter(). |
block_class_styles_get_css_by_style | Returns an array of css classes for a given style name. |
block_class_styles_get_style | Return a style by it's css |
block_class_styles_help | Implements hook_help(). |
block_class_styles_info | Return an array of style presets |
block_class_styles_menu | Implements hook_menu(). |
block_class_styles_permission | Implements hook_permission(). |
block_class_styles_preprocess_block | Implements hook_preprocess_block(). |
_block_class_styles_bean_bundles | |
_block_class_styles_form_submit | Form submission handler |
_block_class_styles_theme_hook_suggestion | Return the theme_hook_suggestion for a style |
_block_class_tablename | Return the name of the table to use based on module version |
Constants
Name![]() |
Description |
---|---|
BLOCK_CLASS_STYLES_ALLOW_MULTIPLE | True/False Should we allow more than one class? |
BLOCK_CLASS_STYLES_DESCRIPTION | The default description that appears under the select element |
BLOCK_CLASS_STYLES_ENTITY_SETTING_URL | This is the path that will be used to toggle a bundle's support |
BLOCK_CLASS_STYLES_FS_DESCRIPTION | Default fieldset description |
BLOCK_CLASS_STYLES_FS_TITLE | Default fieldset title |
BLOCK_CLASS_STYLES_HIDE_CLASSES | Default value for hiding the block_class textfield |
BLOCK_CLASS_STYLES_PATH_SETTINGS | Path to the settings page |
BLOCK_CLASS_STYLES_TITLE | The default select title |
BLOCK_CLASS_STYLES_TITLE_FORMAT | Default format for titles, leave NULL to use drupal core sanitization |