content_taxonomy.module 5.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143
  1. <?php
  2. /**
  3. * Implements hook_form_ID_alter().
  4. */
  5. function content_taxonomy_form_field_ui_field_edit_form_alter(&$form, &$form_state, $form_id) {
  6. $field = $form['#field'];
  7. $instance = $form['#instance'];
  8. // Add parent selector to term reference fields,
  9. // except to the autocomplete widget, as it ignores the parent setting.
  10. if ($field['type'] == 'taxonomy_term_reference'
  11. && !($instance['widget']['type'] == 'taxonomy_autocomplete' || $instance['widget']['type'] == 'autocomplete_deluxe_taxonomy')) {
  12. // add parent form.
  13. foreach ($field['settings']['allowed_values'] as $delta => $tree) {
  14. $options[0] = '---';
  15. // todo this might break with huge vocs
  16. $voc = taxonomy_vocabulary_machine_name_load($tree['vocabulary']);
  17. foreach (taxonomy_get_tree($voc->vid) as $term) {
  18. $options[$term->tid] = str_repeat('- ', $term->depth) . $term->name;
  19. }
  20. $form['field']['settings']['allowed_values'][$delta]['parent'] = array(
  21. '#type' => 'select',
  22. '#title' => t('Parent'),
  23. '#options' => $options,
  24. '#default_value' => isset($tree['parent']) ? $tree['parent'] : 0,
  25. );
  26. $form['field']['settings']['allowed_values'][$delta]['depth'] = array(
  27. '#type' => 'textfield',
  28. '#title' => t('Tree depth'),
  29. '#default_value' => isset($tree['depth']) ? $tree['depth'] : '',
  30. '#description' => t('Set the depth of the tree. Leave empty to load all terms.'),
  31. '#element_validate' => array('_element_validate_integer_positive'),
  32. );
  33. }
  34. }
  35. // Add opt group setting.
  36. if ($field['type'] == 'taxonomy_term_reference' && $instance['widget']['type'] == 'options_select') {
  37. $form['instance']['widget']['settings']['content_taxonomy_opt_groups'] = array(
  38. '#type' => 'checkbox',
  39. '#title' => t('Render parent terms as opt-groups'),
  40. '#default_value' => isset($instance['widget']['settings']['content_taxonomy_opt_groups']) ? $instance['widget']['settings']['content_taxonomy_opt_groups'] : FALSE,
  41. '#description' => t('This option only works if you have a 2-level hierarchy in your vocabulary. Then the parents in the first level get opt-groups and the child terms will be selectable.'),
  42. );
  43. }
  44. }
  45. /**
  46. * Implements hook_field_info_alter().
  47. */
  48. function content_taxonomy_field_info_alter(&$info) {
  49. // Use own options callback for handling additional configuration options.
  50. $info['taxonomy_term_reference']['settings']['options_list_callback'] = 'content_taxonomy_allowed_values';
  51. // Add depth option.
  52. foreach ($info['taxonomy_term_reference']['settings']['allowed_values'] as $key => $values) {
  53. $info['taxonomy_term_reference']['settings']['allowed_values'][$key]['depth'] = 0;
  54. }
  55. }
  56. /**
  57. * Returns the set of valid terms for a taxonomy field.
  58. * Extends taxonomy_allowed_values() with the tree depth option.
  59. *
  60. * @param $field
  61. * The field definition.
  62. * @return
  63. * The array of valid terms for this field, keyed by term id.
  64. */
  65. function content_taxonomy_allowed_values($field) {
  66. $options = array();
  67. foreach ($field['settings']['allowed_values'] as $tree) {
  68. if ($vocabulary = taxonomy_vocabulary_machine_name_load($tree['vocabulary'])) {
  69. $max_depth = (isset($tree['depth']) && !empty($tree['depth'])) ? $tree['depth'] : NULL;
  70. if ($terms = taxonomy_get_tree($vocabulary->vid, $tree['parent'], $max_depth)) {
  71. foreach ($terms as $term) {
  72. $options[$term->tid] = str_repeat('- ', $term->depth) . $term->name;
  73. }
  74. }
  75. }
  76. }
  77. return $options;
  78. }
  79. /**
  80. * Implements hook_field_widget_info_alter().
  81. */
  82. function content_taxonomy_field_widget_info_alter(&$info) {
  83. if (isset($info['options_select']['settings'])) {
  84. $info['options_select']['settings'] += array(
  85. 'content_taxonomy_opt_groups' => FALSE,
  86. );
  87. }
  88. }
  89. /**
  90. * Implements hook_field_widget_form_alter().
  91. */
  92. function content_taxonomy_field_widget_form_alter(&$element, &$form_state, $context) {
  93. $field = $context['field'];
  94. $instance = $context['instance'];
  95. if (!empty($instance['widget']['settings']['content_taxonomy_opt_groups'])) {
  96. $options = content_taxonomy_allowed_values_opt_groups($field);
  97. if (isset($element['#options']['_none'])) {
  98. $options = array('_none' => $element['#options']['_none']) + $options;
  99. }
  100. $element['#options'] = $options;
  101. }
  102. }
  103. /**
  104. * Helper function for generating opt groups.
  105. *
  106. * Similar to content_taxonomy_allowed_values(), but unfortunately we cannot
  107. * directly change content_taxonomy_allowed_values() as it only has the field
  108. * variable and opt groups are settings on the instance level. Still, this is
  109. * not a big performance issue, as taxonomy_get_tree statically caches some
  110. * data.
  111. */
  112. function content_taxonomy_allowed_values_opt_groups($field) {
  113. $options = array();
  114. foreach ($field['settings']['allowed_values'] as $tree) {
  115. if ($vocabulary = taxonomy_vocabulary_machine_name_load($tree['vocabulary'])) {
  116. if ($terms = taxonomy_get_tree($vocabulary->vid, 0, 2)) {
  117. $current_group_term = NULL;
  118. foreach ($terms as $term) {
  119. if ($term->depth == 0) {
  120. $current_group_term = $term;
  121. }
  122. elseif ($term->depth == 1 && !is_null($current_group_term)) {
  123. $options[$current_group_term->name][$term->tid] = $term->name;
  124. }
  125. }
  126. }
  127. }
  128. }
  129. return $options;
  130. }