You are here

easychart.module in Easychart 7.3

Same filename and directory in other branches
  1. 8.3 easychart.module
  2. 7 easychart.module
  3. 7.2 easychart.module

Easychart module file.

File

easychart.module
View source
<?php

/**
 * @file
 * Easychart module file.
 */

/**
 * Implements hook_node_info().
 */
function easychart_node_info() {
  return array(
    'easychart' => array(
      'name' => t('Chart'),
      'base' => 'node_content',
      'description' => t('Create a chart using the world\'s best web charting tool: Highcharts'),
      'locked' => TRUE,
    ),
  );
}

/**
 * Implements hook_init().
 */
function easychart_init() {

  // This adds fullscreen support for the overlay module.
  if (module_exists('overlay')) {
    drupal_add_js(drupal_get_path('module', 'easychart') . '/js/easychart.overlay.js');
  }
}

/**
 * Implements hook_node_type_insert().
 */
function easychart_node_type_insert($content_type) {
  if ($content_type->type == 'easychart') {
    $body_instance = node_add_body_field($content_type, t('Chart description'));

    // Save our changes to the body field instance.
    field_update_instance($body_instance);

    // Create all the fields we are adding to our content type.
    foreach (_easychart_installed_fields() as $field) {
      field_create_field($field);
    }

    // Create all the instances for our fields.
    foreach (_easychart_installed_instances() as $instance) {
      $instance['entity_type'] = 'node';
      $instance['bundle'] = 'easychart';
      field_create_instance($instance);
    }
  }
}

/**
 * Define the fields for our content type.
 *
 * @return array
 *   An associative array specifying the fields we wish to add to our
 *   new node type.
 *
 * @see easychart_node_type_insert().
 */
function _easychart_installed_fields() {
  return array(
    'easychart' => array(
      'field_name' => 'easychart',
      'cardinality' => 1,
      'type' => 'easychart',
    ),
  );
}

/**
 * Define the field instances for our content type.
 *
 * @return array
 *   An associative array specifying the instances we wish to add to our new
 *   node type.
 *
 * @see easychart_node_type_insert().
 */
function _easychart_installed_instances() {
  return array(
    'easychart' => array(
      'field_name' => 'easychart',
      'label' => t('Chart'),
      'type' => 'easychart',
      'widget' => array(
        'type' => 'easychart',
      ),
      'required' => TRUE,
    ),
  );
}

/**
 * Implements hook_form().
 */
function easychart_form($node, $form_state) {
  return node_content_form($node, $form_state);
}

/**
 * Implements hook_field_info().
 */
function easychart_field_info() {
  return array(
    // We name our field as the associative name of the array.
    'easychart' => array(
      'label' => t('Chart'),
      'default_widget' => 'easychart',
      'default_formatter' => 'easychart_default',
    ),
  );
}

/**
 * Implements hook_field_is_empty().
 */
function easychart_field_is_empty($item, $field) {
  if (empty($item['csv'])) {
    return TRUE;
  }
  else {
    return FALSE;
  }
}

/**
 * Implements hook_field_widget_info().
 */
function easychart_field_widget_info() {
  return array(
    'easychart' => array(
      'label' => t('Chart'),
      'field types' => array(
        'easychart',
      ),
    ),
  );
}

/**
 * Implements hook_field_widget_form().
 */
function easychart_field_widget_form(&$form, &$form_state, $field, $instance, $langcode, $items, $delta, $element) {
  switch ($instance['widget']['type']) {
    case 'easychart':
      $required = $element['#required'];

      // Send Easychart configuration to the Easychart admin interface.
      $options = '';
      if (file_exists('public://easychart-options.json')) {
        $options = file_get_contents('public://easychart-options.json');
      }
      $settings = array(
        'easychartOptions' => $options,
        'easychartTemplates' => variable_get('easychart_templates', ''),
        'easychartPresets' => variable_get('easychart_presets', ''),
        'easychartCustomize' => FALSE,
      );
      if (user_access('access full easychart configuration')) {
        $settings['easychartCustomize'] = TRUE;
      }
      drupal_add_js(array(
        'easychart' => $settings,
      ), 'setting');

      // Wrapper to add the required javascript and css.
      $element = array(
        '#prefix' => '<div class="easychart-wrapper clearfix">',
        '#suffix' => '</div>',
        '#attached' => array(
          // Add highcharts plugin.
          'libraries_load' => array(
            array(
              'highcharts',
            ),
            array(
              'easychart',
            ),
          ),
          'js' => array(
            drupal_get_path('module', 'easychart') . '/js/easychart.widget.js',
            drupal_get_path('module', 'easychart') . '/js/screenfull.min.js',
            drupal_get_path('module', 'easychart') . '/js/handsontable.full.min.js',
          ),
          'css' => array(
            drupal_get_path('module', 'easychart') . '/css/easychart.widget.css',
            drupal_get_path('module', 'easychart') . '/css/handsontable.full.min.css',
          ),
        ),
      );

      // Hidden fields with the chart data.
      $element['config'] = array(
        '#description' => t('The configuration options as described at http://api.highcharts.com/highcharts'),
        '#type' => 'hidden',
        '#default_value' => isset($items[$delta]['config']) ? $items[$delta]['config'] : NULL,
        '#attributes' => array(
          'class' => array(
            'easychart-config',
          ),
        ),
      );
      $element['csv'] = array(
        '#description' => t('Your chart data in CSV format'),
        '#type' => 'hidden',
        '#default_value' => isset($items[$delta]['csv']) ? $items[$delta]['csv'] : NULL,
        '#attributes' => array(
          'class' => array(
            'easychart-csv',
          ),
        ),
        '#element_validate' => array(
          'easychart_field_csv_validate',
        ),
        '#csv_required' => $required,
      );
      $element['csv_url'] = array(
        '#description' => t('The URL to a CSV file'),
        '#type' => 'hidden',
        '#default_value' => isset($items[$delta]['csv_url']) ? $items[$delta]['csv_url'] : NULL,
        '#attributes' => array(
          'class' => array(
            'easychart-csv-url',
          ),
        ),
      );

      // Placeholder to embed the Easychart plugin.
      $element['preview'] = array(
        '#title' => t('Easychart'),
        '#markup' => '',
        '#prefix' => '<div class="easychart-embed"><div class="easychart-header"><span class="toggle">' . t('Toggle Fullscreen') . '</span></div>',
        '#suffix' => '</div>',
      );
      break;
  }
  return $element;
}

/**
 * CSV element validation function.
 *
 * @param $element
 *   The CSV element
 */
function easychart_field_csv_validate($element) {
  if ($element['#csv_required'] && empty($element['#value'])) {
    form_set_error('csv', t('Please create an Easychart chart before saving.'));
  }
}

/**
 * Implements hook_field_formatter_info().
 */
function easychart_field_formatter_info() {
  return array(
    'easychart_default' => array(
      'label' => t('Default'),
      'field types' => array(
        'easychart',
      ),
    ),
  );
}

/**
 * Implements hook_field_formatter_view().
 */
function easychart_field_formatter_view($entity_type, $entity, $field, $instance, $langcode, $items, $display) {
  $element = array();
  switch ($display['type']) {
    case 'easychart_default':
      foreach ($items as $delta => $item) {
        $output = _easychart_print_chart($item, $delta);
        $element[$delta] = array(
          '#markup' => $output,
        );
      }
      break;
  }
  return $element;
}

/**
 * Implements hook_libraries_info().
 *
 * For defining external libraries.
 */
function easychart_libraries_info() {
  $libraries['highcharts'] = array(
    'name' => 'Highcharts',
    'vendor url' => 'http://www.highcharts.com',
    'download url' => 'http://www.highcharts.com/download',
    'recommended' => array(
      'version' => '4.2.7',
      // 4.2.x and up
      'uri' => 'http://code.highcharts.com/zips/Highcharts-4.2.7.zip',
    ),
    'version arguments' => array(
      'file' => 'js/highcharts.js',
      // Could be any file with version info
      'pattern' => '/Highcharts JS v(\\d\\.\\d\\.\\d)/',
      'lines' => 2,
    ),
    'files' => array(
      'js' => array(
        'js/highcharts.js',
        'js/highcharts-3d.js',
        'js/highcharts-more.js',
        'js/modules/data.js',
        'js/modules/funnel.js',
        'js/modules/heatmap.js',
        'js/modules/solid-gauge.js',
        'js/modules/treemap.js',
        'js/modules/boost.js',
        'js/modules/exporting.js',
        'js/modules/no-data-to-display.js',
      ),
    ),
  );
  $libraries['easychart'] = array(
    'name' => 'Easychart',
    'vendor url' => 'http://www.easychart.org',
    'download url' => 'https://github.com/bestuurszaken/easychart',
    'recommended' => array(
      'version' => '3.1.0',
      'uri' => 'https://github.com/bestuurszaken/easychart/archive/v3.1.3.zip',
    ),
    'latest' => array(
      'version' => 'master',
      'uri' => 'https://github.com/bestuurszaken/easychart/archive/master.zip',
    ),
    'version arguments' => array(
      'file' => 'dist/ec.min.js',
      'pattern' => '/@version\\sv(\\d\\.\\d\\.\\d)/',
      'lines' => 3,
    ),
    'files' => array(
      'js' => array(
        'dist/ec.min.js',
      ),
    ),
    'variants' => array(
      // Only minimal functionality to render a chart.
      'render' => array(
        'files' => array(
          'js' => array(
            'dist/ec.render.min.js',
          ),
        ),
      ),
    ),
  );
  return $libraries;
}

/*
 * Implements hook_menu().
 */
function easychart_menu() {
  $items = array();
  $items['admin/config/media/easychart'] = array(
    'title' => 'Easychart',
    'description' => 'Configure the options that will be available when creating charts.',
    'page callback' => 'drupal_get_form',
    'page arguments' => array(
      'easychart_admin_options',
    ),
    'access arguments' => array(
      'administer Easychart settings',
    ),
    'type' => MENU_NORMAL_ITEM,
    'file' => 'easychart.admin.inc',
  );
  $items['admin/config/media/easychart/options'] = array(
    'title' => 'Options',
    'description' => 'Configure the options that will be available when creating charts.',
    'type' => MENU_DEFAULT_LOCAL_TASK,
    'weight' => 10,
  );
  $items['admin/config/media/easychart/templates'] = array(
    'title' => 'Templates',
    'page callback' => 'drupal_get_form',
    'page arguments' => array(
      'easychart_admin_templates',
    ),
    'access arguments' => array(
      'administer Easychart settings',
    ),
    'type' => MENU_LOCAL_TASK,
    'file' => 'easychart.admin.inc',
    'weight' => 20,
  );
  $items['admin/config/media/easychart/presets'] = array(
    'title' => 'Presets',
    'page callback' => 'drupal_get_form',
    'page arguments' => array(
      'easychart_admin_presets',
    ),
    'access arguments' => array(
      'administer Easychart settings',
    ),
    'type' => MENU_LOCAL_TASK,
    'file' => 'easychart.admin.inc',
    'weight' => 30,
  );
  $items['admin/config/media/easychart/settings'] = array(
    'title' => 'Settings',
    'page callback' => 'drupal_get_form',
    'page arguments' => array(
      'easychart_admin_settings',
    ),
    'access arguments' => array(
      'administer Easychart settings',
    ),
    'type' => MENU_LOCAL_TASK,
    'file' => 'easychart.admin.inc',
    'weight' => 40,
  );
  return $items;
}

/**
 * Helper functions to print the actual chart.
 *
 * @param $item
 *   The item
 * @param $delta
 *   The delta.
 *
 * @return string $output
 */
function _easychart_print_chart($item, $delta) {
  global $chart_count;
  $chart_count++;
  $output = '';
  if (!empty($item['config'])) {
    if ($chart_count == 1) {

      // Add the highcharts javascript.
      libraries_load('highcharts');
      libraries_load('easychart', 'render');
    }

    // Print a div and add inline javascript
    $output = '<div id="easychart-chart-' . $chart_count . '">';
    $output .= '</div>';

    // Get the csv data.
    $csv = '';
    if (!empty($item['csv'])) {
      $csv = $item['csv'];
    }
    $inline_js = ' document.addEventListener("DOMContentLoaded", function () {
                     var container = document.getElementById(\'easychart-chart-' . $chart_count . '\');
                     window.easychart = new ec({element: container});';
    $inline_js .= '  window.easychart.setConfigStringified(\'' . $item['config'] . '\');';
    $inline_js .= '  window.easychart.setData(' . $csv . ');';
    if (variable_get('easychart_presets', '') != '') {
      $inline_js .= '  window.easychart.setPresets(' . str_replace('\\r\\n', '', variable_get('easychart_presets', '')) . ');';
    }
    $inline_js .= '})';
    drupal_add_js($inline_js, array(
      'type' => 'inline',
      'scope' => 'footer',
    ));
  }
  return $output;
}

/**
 * Implements hook_permission().
 */
function easychart_permission() {
  return array(
    'access full easychart configuration' => array(
      'title' => t('Allow using all Easychart customisation options.'),
    ),
    'administer Easychart settings' => array(
      'title' => t('Administer Easychart settings'),
      'description' => t('Configure default settings for the Easychart popup.'),
    ),
  );
}

/**
 * Implements hook_cron().
 */
function easychart_cron() {

  // We don't want to act every time cron runs (which could be every
  // minute) so keep a time for the next run in a variable.
  $interval = variable_get('easychart_url_update_frequency', 60 * 60 * 1);
  if (!empty($interval) && REQUEST_TIME >= variable_get('easychart_cron_next_execution', 0)) {

    // Update the data from Easychart fields that use an external url.
    module_load_include('inc', 'easychart', 'easychart.helpers');
    _easychart_update_csv_from_url();

    // Set the next execution time.
    variable_set('easychart_cron_next_execution', REQUEST_TIME + $interval);
  }
}