You are here

collapsiblock.module in Collapsiblock 3.x

Make blocks collapsible.

File

collapsiblock.module
View source
<?php

/**
 * @file
 * Make blocks collapsible.
 */
use Drupal\Core\Block\BlockPluginInterface;
use Drupal\Core\Form\FormStateInterface;
use Drupal\block\BlockInterface;
use Drupal\block\Entity\Block;

// Scalar (JSON) constant for php 5.*.
define('COLLAPSIBLOCK_ACTION_OPTIONS', serialize([
  1 => t('None.'),
  2 => t('Collapsible, expanded by default.'),
  3 => t('Collapsible, collapsed by default.'),
  5 => t('Collapsible, expanded all the time.'),
  4 => t('Collapsible, collapsed all the time.'),
]));

/**
 * Implements hook_page_attachments_alter().
 *
 * Attach our library and global settings.
 */
function collapsiblock_page_attachments_alter(array &$attachments) {
  $attachments['#attached']['library'][] = 'collapsiblock/core';
  $settings = \Drupal::config('collapsiblock.settings');
  $collapsiblock = [
    'active_pages' => $settings
      ->get('active_pages'),
    'slide_type' => $settings
      ->get('slide_type'),
    'slide_speed' => $settings
      ->get('slide_speed'),
  ];
  $attachments['#attached']['drupalSettings']['collapsiblock'] = $collapsiblock;
}

/**
 * Implements hook_form_FORM_ID_alter().
 */
function collapsiblock_form_block_form_alter(&$form, FormStateInterface $form_state, $form_id) {
  $form['collapsiblock_settings'] = [
    '#type' => 'details',
    '#title' => t('Collapsible'),
    '#open' => TRUE,
  ];

  // Add the global default to the list of options for the per-block setting.
  $block = $form_state
    ->getFormObject()
    ->getEntity();
  $options = unserialize(COLLAPSIBLOCK_ACTION_OPTIONS);
  $settings = \Drupal::config('collapsiblock.settings');
  $default_action = $options[$settings
    ->get('default_action')];
  $options = [
    0 => 'Global default, currently set to: ' . $default_action,
  ] + $options;
  $form['collapsiblock_settings']['collapse_action'] = [
    '#type' => 'radios',
    '#title' => t('Block collapse behavior'),
    '#options' => $options,
    '#default_value' => $block
      ->getThirdPartySetting('collapsiblock', 'collapse_action', 0),
  ];
  $form['#entity_builders'][] = 'collapsiblock_block_form_form_builder';
}

/**
 * Entity builder for the block form with third party options.
 *
 * @see collapsiblock_form_block_form_alter()
 */
function collapsiblock_block_form_form_builder($entity_type, Block $block, &$form, FormStateInterface $form_state) {
  $block
    ->setThirdPartySetting('collapsiblock', 'collapse_action', $form_state
    ->getValue('collapsiblock_settings')['collapse_action']);
}

/**
 * Implements hook_block_view_alter().
 */
function collapsiblock_block_view_alter(array &$build, BlockPluginInterface $block) {
  if (empty($build['#block']) || !$build['#block'] instanceof BlockInterface) {
    return;
  }
  $block_entity = $build['#block'];
  $action = $block_entity
    ->getThirdPartySetting('collapsiblock', 'collapse_action');

  // If the block is set to global default, get that default and use it instead
  // of 0.
  if ($action == 0) {
    $action = \Drupal::config('collapsiblock.settings')
      ->get('default_action');
  }

  // If the action is anything other than 'none', create our wrapper elements.
  if ($action != 1) {
    $id = 'collapsiblock-wrapper-' . $block_entity
      ->id();
    $classes[] = 'collapsiblock';
    $build['#collapsiblock']['prefix'] = [
      '#markup' => '<div id="' . $id . '" class="' . implode(' ', $classes) . '" data-collapsiblock-action="' . $action . '">',
    ];
    $build['#collapsiblock']['suffix'] = [
      'collapsiblock' => [
        '#markup' => '</div>',
      ],
    ];
  }
}

/**
 * Implements hook_preprocess_HOOK().
 *
 * Wrap the title in a div that contains the Collapsiblock elements.
 */
function collapsiblock_preprocess_block(&$variables) {
  if (isset($variables['elements']['#collapsiblock'])) {
    $variables['title_prefix'][] = $variables['elements']['#collapsiblock']['prefix'];
    $variables['title_suffix'][] = $variables['elements']['#collapsiblock']['suffix'];
  }
}