You are here

i18ntaxonomy.module in Internationalization 5.3

Same filename and directory in other branches
  1. 5 contrib/i18ntaxonomy.module
  2. 5.2 contrib/i18ntaxonomy.module

Internationalization (i18n) package - taxonomy term translation

Translates taxonomy term for selected vocabularies running them through the localization system It also translates terms for views filters and views results

@author Jose A. Reyero, 2007

File

contrib/i18ntaxonomy.module
View source
<?php

/**
 * @file
 * Internationalization (i18n) package - taxonomy term translation
 * 
 * Translates taxonomy term for selected vocabularies running them through the localization system
 * It also translates terms for views filters and views results
 * 
 * @author Jose A. Reyero, 2007
 *
 */

/**
 * Implementation of hook_form_alter().
 */
function i18ntaxonomy_form_alter($form_id, &$form) {
  if ($form_id == 'translation_admin_settings') {

    // Translation settings
    $translate = variable_get('i18ntaxonomy_vocabularies', array());
    $form['i18ntaxonomy_vocabularies'] = array(
      '#type' => 'fieldset',
      '#collapsible' => TRUE,
      '#title' => t('Vocabulary Translation'),
      '#tree' => TRUE,
      '#weight' => 0,
      '#description' => t('Vocabularies to translate through localization system'),
    );
    foreach (taxonomy_get_vocabularies() as $voc) {
      $form['i18ntaxonomy_vocabularies'][$voc->vid] = array(
        '#type' => 'checkbox',
        '#title' => $voc->name,
        '#default_value' => $translate[$voc->vid],
      );
    }
  }
  elseif (isset($form['type']) && $form['type']['#value'] . '_node_form' == $form_id && ($node = $form['#node']) && isset($form['taxonomy']) && ($translate = variable_get('i18ntaxonomy_vocabularies', array()))) {

    // Node form. Translate vocabularies
    if (!isset($node->taxonomy)) {
      if ($node->nid) {
        $terms = taxonomy_node_get_terms($node->nid);
      }
      else {
        $terms = array();
      }
    }
    else {
      $terms = $node->taxonomy;
    }

    // Regenerate the whole field for translatable vocabularies
    foreach (element_children($form['taxonomy']) as $vid) {
      if (is_numeric($vid) && $translate[$vid]) {

        // Rebuild this vocabulary's form
        $vocabulary = taxonomy_get_vocabulary($vid);

        // Extract terms belonging to the vocabulary in question.
        $default_terms = array();
        foreach ($terms as $term) {
          if ($term->vid == $vid) {
            $default_terms[$term->tid] = $term;
          }
        }
        $form['taxonomy'][$vid] = i18ntaxonomy_form($vocabulary->vid, array_keys($default_terms));
        $form['taxonomy'][$vid]['#weight'] = $vocabulary->weight;
        $form['taxonomy'][$vid]['#required'] = $vocabulary->required;
      }
    }
  }
  else {
    if ($form_id == 'views_filters' && ($translate = variable_get('i18ntaxonomy_vocabularies', array()))) {

      // We only translate exposed filters here
      $view = $form['view']['#value'];
      if ($view->exposed_filter) {
        foreach ($view->exposed_filter as $index => $filter) {
          $matches = array();
          if ($filter['field'] == 'term_node.tid') {

            // That's a full taxonomy box. Translate options: arary(tid => "Vocabulary: Term")
            // First, we get a translated list. Then we replace on the options array
            $replace = _i18ntaxonomy_vocabulary_terms(array_keys($translate));
            foreach ($replace as $tid => $name) {
              if (isset($form["filter{$index}"]['#options'][$tid])) {
                $form["filter{$index}"]['#options'][$tid] = $name;
              }
            }
          }
          elseif (preg_match("/term_node_(\\d+)\\.tid/", $filter['field'], $matches)) {
            $vid = $matches[1];
            if ($translate[$vid]) {

              // Translate this vocabulary terms, field name is filter$index vid = $matches[1]
              foreach ($form["filter{$index}"]['#options'] as $value => $option) {
                if ($value != '**ALL**') {

                  // ALL option should be already localized
                  // This may be an object with an option property being an array (tid => name)
                  if (is_object($option) && is_array($option->option)) {
                    foreach (array_keys($option->option) as $tid) {
                      $option->option[$tid] = tt("taxonomy:term:{$tid}:name", $option->option[$tid]);
                    }
                    $form["filter{$index}"]['#options'][$value] = $option;

                    // But it used to be a plain string, so let's keep this just in case...
                  }
                  elseif (is_string($option)) {
                    $form["filter{$index}"]['#options'][$value] = t($option);
                  }
                }
              }
            }
          }
        }
      }
    }
  }
}

/**
 * Implementation of hook_nodeapi()
 * 
 * This runs after taxonomy:nodeapi, so we just translate terms here
 */
function i18ntaxonomy_nodeapi(&$node, $op, $teaser, $page) {
  if ($op == 'view' && array_key_exists('taxonomy', $node)) {
    _i18ntaxonomy_translate_terms($node->taxonomy);
  }
}

/**
 * Implementation of hook_views_pre_view().
 * 
 * Translate table header for taxonomy fields
 * //field[i][id] = term_node_1.name, translate table header
 * and replace handler for that field
 */
function i18ntaxonomy_views_pre_view(&$view, &$items) {

  //var_dump($view);
  $translate = variable_get('i18ntaxonomy_vocabularies', array());
  foreach ($view->field as $index => $data) {
    $matches = array();
    if ($data['id'] == 'term_node.name') {

      // That's a full taxonomy box
      $view->field[$index]['handler'] = 'i18ntaxonomy_views_handler_field_allterms';
    }
    elseif (preg_match("/term_node_(\\d+)\\.name/", $data['id'], $matches)) {
      $vid = $matches[1];
      if ($translate[$vid]) {

        // Set new handler for this field
        $view->field[$index]['handler'] = 'i18ntaxonomy_views_handler_field_allterms';
      }
    }
  }
}

/**
 * Field handler for taxonomy term fields
 * 
 * Remake of views_handler_field_allterms with term name translation
 */
function i18ntaxonomy_views_handler_field_allterms($fieldinfo, $fielddata, $value, $data) {
  if ($fieldinfo['vocabulary']) {
    $terms = taxonomy_node_get_terms_by_vocabulary($data->nid, $fieldinfo['vocabulary']);
  }
  else {
    $terms = taxonomy_node_get_terms($data->nid);
  }

  // Translate all these terms
  _i18ntaxonomy_translate_terms($terms);
  if ($fielddata['options'] == 'nolink') {
    foreach ($terms as $term) {
      $links[] = check_plain($term->name);
    }
    $links = !empty($links) ? implode(' | ', $links) : '';
  }
  else {
    $node = new stdClass();
    $node->taxonomy = $terms;
    $links = theme('links', taxonomy_link('taxonomy terms', $node));
  }
  return $links;
}

/**
 * Generate a form element for selecting terms from a vocabulary.
 * Translates all translatable strings.
 */
function i18ntaxonomy_form($vid, $value = 0, $help = NULL, $name = 'taxonomy') {
  $vocabulary = taxonomy_get_vocabulary($vid);
  $help = $vocabulary->help ? t($vocabulary->help) : '';
  if ($vocabulary->required) {
    $blank = 0;
  }
  else {
    $blank = '<' . t('none') . '>';
  }
  return _i18ntaxonomy_term_select(t(check_plain($vocabulary->name)), $name, $value, $vid, $help, intval($vocabulary->multiple), $blank);
}

// Produces translated tree
function _i18ntaxonomy_term_select($title, $name, $value, $vocabulary_id, $description, $multiple, $blank, $exclude = array()) {
  $tree = taxonomy_get_tree($vocabulary_id);
  $options = array();
  if ($blank) {
    $options[0] = $blank;
  }
  if ($tree) {
    foreach ($tree as $term) {
      if (!in_array($term->tid, $exclude)) {
        $choice = new stdClass();
        $choice->option = array(
          $term->tid => str_repeat('-', $term->depth) . t($term->name),
        );
        $options[] = $choice;
      }
    }
    if (!$blank && !$value) {

      // required but without a predefined value, so set first as predefined
      $value = $tree[0]->tid;
    }
  }
  return array(
    '#type' => 'select',
    '#title' => $title,
    '#default_value' => $value,
    '#options' => $options,
    '#description' => $description,
    '#multiple' => $multiple,
    '#size' => $multiple ? min(9, count($options)) : 0,
    '#weight' => -15,
    '#theme' => 'taxonomy_term_select',
  );
}

// Translate an array of term objects
function _i18ntaxonomy_translate_terms(&$terms) {
  if ($translate = variable_get('i18ntaxonomy_vocabularies', array())) {
    foreach (array_keys($terms) as $tid) {
      if ($translate[$terms[$tid]->vid]) {
        $terms[$tid]->name = tt("taxonomy:term:{$tid}:name", $terms[$tid]->name);
      }
    }
  }
}

// Get a list of vocabularies and terms
function _i18ntaxonomy_vocabulary_terms($vid = NULL, $fullname = TRUE) {
  $tids = array();
  if (is_numeric($vid)) {
    $where = "WHERE td.vid = {$vid}";
  }
  elseif (is_array($vid)) {
    $where = "WHERE td.vid IN(" . implode(',', $vid) . ')';
  }
  $result = db_query("SELECT DISTINCT(td.tid), td.name, td.weight, v.name as vocabname, v.weight FROM {term_data} td LEFT JOIN {vocabulary} v ON v.vid = td.vid {$where} ORDER BY v.weight, v.name, td.weight, td.name");
  while ($obj = db_fetch_object($result)) {
    $tids[$obj->tid] = $fullname ? tt("taxonomy:vocabulary:{$obj->vid}:name", $obj->vocabname) . ': ' . tt("taxonomy:term:{$obj->tid}:name", $obj->name) : tt("taxonomy:term:{$obj->tid}:name", $obj->name);
  }
  return $tids;
}

Functions

Namesort descending Description
i18ntaxonomy_form Generate a form element for selecting terms from a vocabulary. Translates all translatable strings.
i18ntaxonomy_form_alter Implementation of hook_form_alter().
i18ntaxonomy_nodeapi Implementation of hook_nodeapi()
i18ntaxonomy_views_handler_field_allterms Field handler for taxonomy term fields
i18ntaxonomy_views_pre_view Implementation of hook_views_pre_view().
_i18ntaxonomy_term_select
_i18ntaxonomy_translate_terms
_i18ntaxonomy_vocabulary_terms