cer_ief.module 3.8 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394
  1. <?php
  2. /**
  3. * @file
  4. * Provides an option to hide CER fields on inline entity forms. Spun off
  5. * from Issue #2240371.
  6. */
  7. /**
  8. * Implements hook_form_FORM_ID_alter().
  9. */
  10. function cer_ief_form_field_ui_field_edit_form_alter(array &$form, array &$form_state) {
  11. // Add options to hide corresponding entity reference fields on inline entity forms.
  12. $instance = $form['#instance'];
  13. if ($instance['widget']['type'] == 'inline_entity_form') {
  14. // Build a filter to fetch matching CER presets for this field instance.
  15. $entity_type = $instance['entity_type'];
  16. $bundle = $instance['bundle'];
  17. $field_name = $instance['field_name'];
  18. $filter = "{$entity_type}:{$bundle}:{$field_name}";
  19. if ($presets = _cer_filter_presets($filter)) {
  20. // There are available CER configurations for this IEF instance.
  21. // Add option to hide field(s) on referenced entities.
  22. $ief_settings = &$form['instance']['widget']['settings']['type_settings'];
  23. $ief_settings['hide_cer_fields'] = array(
  24. '#type' => 'checkbox',
  25. '#title' => t('Hide corresponding entity reference field(s) on form.'),
  26. '#default_value' => !empty($instance['widget']['settings']['type_settings']['hide_cer_fields']),
  27. );
  28. // @todo Add checkbox for each corresponding field?
  29. // foreach ($presets as $preset) etc.
  30. }
  31. }
  32. }
  33. /**
  34. * Implements hook_field_widget_form_alter().
  35. *
  36. * @todo This could be cached into an array and only rebuilt when a contextual
  37. * field instance is updated or CER pattern added/removed.
  38. */
  39. function cer_ief_field_widget_form_alter(array &$element, array &$form_state, array $context) {
  40. // Only concerns fields within Inline Entity Forms.
  41. if (isset($context['form']['#ief_id'])) {
  42. // Get the form ID.
  43. $ief_id = $context['form']['#ief_id'];
  44. // Get instance information for the IEF field.
  45. $ief_field_instance = $form_state['inline_entity_form'][$ief_id]['instance'];
  46. // Check if "hide" is enabled on the IEF that is holding this field.
  47. $hide_cer_fields = !empty($ief_field_instance['widget']['settings']['type_settings']['hide_cer_fields']);
  48. if ($hide_cer_fields) {
  49. // Get available CER chains. We use an ordinary static as this will be called for
  50. // each field that belongs to an IEF with 'hide' enabled -- could be a lot.
  51. static $plugins;
  52. if (! isset($plugins)) {
  53. // Load available CER field keys into a map. The actual plugin info isn't needed.
  54. // We use drupal_map_assoc() so we can do isset() checks for plugins instead
  55. // of calling in_array().
  56. $plugins = drupal_map_assoc(array_keys(CerField::getPluginInfo()));
  57. }
  58. // Set up filter chains for the affected entities. The left chain is for the entity
  59. // that has the IEF field on it, and the right chain is for the entity *in* the IEF.
  60. $left_chain = $ief_field_instance['entity_type'] . ':' . $ief_field_instance['bundle'] . ':' . $ief_field_instance['field_name'];
  61. $right_chain = $context['instance']['entity_type'] . ':' . $context['instance']['bundle'] . ':' . $context['instance']['field_name'];
  62. // Ensure that both fields are CER fields. If they're not, bail out.
  63. if (! isset($plugins[$left_chain], $plugins[$right_chain])) {
  64. return;
  65. }
  66. // If a preset from parent to IEF exists, prevent access to the field.
  67. foreach (_cer_filter_presets($left_chain) as $preset) {
  68. // Check if the preset's right hand points to the instance found in the IEF.
  69. if (strpos($preset->right, $right_chain) === 0) {
  70. $match = TRUE;
  71. }
  72. elseif ($preset->bidirectional && strpos($preset->left, $right_chain) === 0) {
  73. $match = TRUE;
  74. }
  75. // Matching chain found. Prevent access to this field and return.
  76. if (isset($match)) {
  77. $element['#access'] = FALSE;
  78. return;
  79. }
  80. }
  81. }
  82. }
  83. }