You are here

farm_map.module in farmOS 7

File

modules/farm/farm_map/farm_map.module
View source
<?php

/**
 * @file
 * Code for the Farm Maps feature.
 */
include_once 'farm_map.block.inc';
include_once 'farm_map.geo.inc';

/**
 * Implements hook_hook_info().
 */
function farm_map_hook_info() {
  $hooks['farm_map_behaviors'] = array(
    'group' => 'farm_map',
  );
  $hooks['farm_map_behavior_settings'] = array(
    'group' => 'farm_map',
  );
  $hooks['farm_map_view'] = array(
    'group' => 'farm_map',
  );
  return $hooks;
}

/**
 * Implements hook_permission().
 */
function farm_map_permission() {
  $perms = array(
    'administer farm_map module' => array(
      'title' => t('Administer farm map module'),
    ),
  );
  return $perms;
}

/**
 * Implements hook_farm_access_perms().
 */
function farm_map_farm_access_perms($role) {
  $perms = array();

  // Load the list of farm roles.
  $roles = farm_access_roles();

  // If this role has 'config' access,grant access to map configuration.
  if (!empty($roles[$role]['access']['config'])) {
    $perms[] = 'administer farm_map module';
  }
  return $perms;
}

/**
 * Implements hook_menu().
 */
function farm_map_menu() {

  // Map configuration form.
  $items['admin/config/farm/map'] = array(
    'title' => 'Map',
    'description' => 'Map configuration settings.',
    'page callback' => 'drupal_get_form',
    'page arguments' => array(
      'farm_map_settings_form',
    ),
    'access arguments' => array(
      'administer farm_map module',
    ),
  );
  return $items;
}

/**
 * Implements hook_libraries_info().
 */
function farm_map_libraries_info() {
  $libraries['farmOS-map'] = array(
    'name' => 'farmOS Map',
    'vendor url' => 'https://github.com/farmOS/farmOS-map',
    'download url' => 'https://github.com/farmOS/farmOS-map/releases',
    'version arguments' => array(
      'file' => 'farmOS-map.js',
      'pattern' => '/farmOS-map v([0-9\\.]+)/',
      'lines' => 1,
    ),
    'files' => array(
      'js' => array(
        'farmOS-map.js',
      ),
    ),
  );
  return $libraries;
}

/**
 * Implements hook_theme().
 */
function farm_map_theme($existing, $type, $theme, $path) {
  return array(
    'farm_map' => array(
      'render element' => 'element',
    ),
  );
}

/**
 * Returns HTML that wraps the farm map..
 */
function theme_farm_map(&$vars) {

  // Get the element.
  $element = $vars['element'];

  // Load the farmOS-map.js library.
  libraries_load('farmOS-map');

  // Get the map name (default to 'farm_map').
  if (empty($element['#map_name'])) {
    $element['#map_name'] = 'farm_map';
  }
  $map_name = $element['#map_name'];

  // Generate a map div ID, if one wasn't provided.
  $id = drupal_html_id($map_name);
  if (!empty($element['#attributes']['id'])) {
    $id = $element['#attributes']['id'];
  }
  else {
    $element['#attributes']['id'] = $id;
  }

  // Add 'farm-map' CSS class.
  if (empty($element['#attributes']['class']) || !in_array('farm-map', $element['#attributes']['class'])) {
    $element['#attributes']['class'][] = 'farm-map';
  }

  // Create a settings array to be passed to JavaScript.
  $settings = array(
    'farm_map' => array(),
  );

  // Add a setting that defines the base path of the site.
  // We do this instead of using Drupal.settings.basePath in Javascript
  // because that variable does not take into account whether or not clean
  // URLs are enabled.
  $settings['farm_map']['base_path'] = str_replace('farm', '', url('farm'));

  // Load the system of measurement, and save it to settings.
  $system_of_measurement = farm_quantity_system_of_measurement();
  $settings['farm_map']['units'] = $system_of_measurement;

  // If WKT is set, add it to the settings associated with the element ID.
  if (isset($element['#wkt'])) {
    $settings['farm_map']['wkt'][$id] = $element['#wkt'];
  }

  // Add the JavaScript settings.
  drupal_add_js($settings, 'setting');

  // Add farm_map.js, which will run farmOS.map.create().
  drupal_add_js(drupal_get_path('module', 'farm_map') . '/js/farm_map.js');

  // Add farm_map.css.
  drupal_add_css(drupal_get_path('module', 'farm_map') . '/css/farm_map.css');

  // Allow other modules to perform logic.
  module_invoke_all('farm_map_view', $map_name, $element);

  // Return a simple div with attributes.
  return '<div' . drupal_attributes($element['#attributes']) . '></div>';
}

/**
 * Implements hook_element_info().
 */
function farm_map_element_info() {
  return array(
    'farm_map' => array(
      '#theme' => 'farm_map',
    ),
  );
}

/**
 * Build a map render array.
 *
 * @param string $map_name
 *   The machine name of the map.
 * @param bool $fieldset
 *   Whether or not to wrap the map in a fieldset.
 * @param string $title
 *   Whether or not to wrap the map in a fieldset.
 * @param bool $collapsed
 *   Whether or not to collapse the fieldset by default.
 *
 * @return array
 *   Returns a Drupal render array.
 */
function farm_map_build($map_name, $fieldset = FALSE, $title = '', $collapsed = FALSE) {

  // Build the map.
  $build = array(
    '#type' => 'farm_map',
    '#map_name' => $map_name,
  );

  // Wrap the map in a fieldset, if desired.
  if (!empty($fieldset)) {

    // Create the fieldset.
    $build = array(
      '#type' => 'fieldset',
      '#title' => $title,
      '#collapsible' => TRUE,
      '#collapsed' => $collapsed,
      'farm_map' => $build,
    );

    // Add 'collapsible' and 'collapsed' classes. This is necessary when
    // rendering the fieldset outside of a form.
    // See: https://www.drupal.org/node/1099132
    drupal_add_library('system', 'drupal.collapse');
    $build['#attributes']['class'][] = 'collapsible';
    $build['#attributes']['class'][] = 'collapsed';
  }

  // Return the build.
  return $build;
}

/**
 * Add a farmOS-map behavior to the page.
 *
 * @param string $behavior
 *   The behavior name.
 * @param array $settings
 *   Optionally provide settings to override defaults.
 */
function farm_map_add_behavior($behavior, $settings = array()) {

  // Ask modules for behaviors.
  $hook = 'farm_map_behaviors';
  $modules = module_implements($hook);
  foreach ($modules as $module) {

    // Get the module's behaviors.
    $behaviors = module_invoke($module, $hook);

    // If the desired behavior isn't defined, skip.
    if (!(array_key_exists($behavior, $behaviors) && !empty($behaviors[$behavior]['js']))) {
      continue;
    }

    // If the module defines settings for the behavior, add them as JS settings.
    $settings_hook = 'farm_map_behavior_settings';
    $default_settings = array();
    if (function_exists($module . '_' . $settings_hook)) {
      $default_settings = module_invoke($module, $settings_hook, $behavior);
    }
    $settings = array_merge($default_settings, $settings);
    if (!empty($settings)) {
      drupal_add_js(array(
        'farm_map' => array(
          'behaviors' => array(
            $behavior => $settings,
          ),
        ),
      ), array(
        'type' => 'setting',
      ));
    }

    // Add the behavior JS to the page.
    $path = drupal_get_path('module', $module) . '/' . $behaviors[$behavior]['js'];
    drupal_add_js($path);
  }
}

/**
 * Map settings form.
 */
function farm_map_settings_form($form, &$form_state) {
  $form = array();
  return system_settings_form($form);
}

/**
 * Extract geometries from an entity.
 *
 * @param $entity_type
 *   The entity type machine name.
 * @param $entity
 *   The entity object.
 *
 * @return array
 *   Return an array of geometry strings in WKT format. An associative array
 *   is allowed, and the keys can be used to differentiate multiple geometries
 *   from the same entity.
 */
function farm_map_entity_geometries($entity_type, $entity) {

  // Ask modules to extract geometries.
  return module_invoke_all('farm_map_entity_geometries', $entity_type, $entity);
}

/**
 * Implements hook_farm_map_geometries().
 */
function farm_map_farm_map_entity_geometries($entity_type, $entity) {
  $geometries = array();

  // Find geometry in the standard geofield.
  if (!empty($entity->field_farm_geofield[LANGUAGE_NONE][0]['geom'])) {
    $geometries[] = $entity->field_farm_geofield[LANGUAGE_NONE][0]['geom'];
  }
  return $geometries;
}

/**
 * Helper function for populating the geometry field of an entity.
 *
 * @param Entity $entity
 *   The entity object.
 * @param array $geoms
 *   An array of geometry strings in WKT format.
 */
function farm_map_geofield_populate(&$entity, $geoms = array()) {

  // If no geometries were found, bail.
  if (empty($geoms)) {
    return;
  }

  // Combine the WKT geometries into a single GeoPHP geometry.
  $geometry = farm_map_combine_geoms($geoms);

  // If that didn't work, bail.
  if (empty($geometry)) {
    return;
  }

  // Save the combined geometry to the movement log.
  if (!empty($geometry)) {
    $entity->field_farm_geofield[LANGUAGE_NONE][0] = geofield_get_values_from_geometry($geometry);
  }
}

Functions

Namesort descending Description
farm_map_add_behavior Add a farmOS-map behavior to the page.
farm_map_build Build a map render array.
farm_map_element_info Implements hook_element_info().
farm_map_entity_geometries Extract geometries from an entity.
farm_map_farm_access_perms Implements hook_farm_access_perms().
farm_map_farm_map_entity_geometries Implements hook_farm_map_geometries().
farm_map_geofield_populate Helper function for populating the geometry field of an entity.
farm_map_hook_info Implements hook_hook_info().
farm_map_libraries_info Implements hook_libraries_info().
farm_map_menu Implements hook_menu().
farm_map_permission Implements hook_permission().
farm_map_settings_form Map settings form.
farm_map_theme Implements hook_theme().
theme_farm_map Returns HTML that wraps the farm map..