forked from a64f7bb4-7358-4778-9fbe-3b882c34cc1d/v1
				
			
		
			
				
	
	
		
			657 lines
		
	
	
		
			21 KiB
		
	
	
	
		
			PHP
		
	
	
			
		
		
	
	
			657 lines
		
	
	
		
			21 KiB
		
	
	
	
		
			PHP
		
	
	
| <?php
 | |
| 
 | |
| /**
 | |
|  * @file
 | |
|  * The Flag module.
 | |
|  */
 | |
| 
 | |
| 
 | |
| use Drupal\Core\Entity\ContentEntityFormInterface;
 | |
| use Drupal\Core\Form\ConfirmFormInterface;
 | |
| use Drupal\Core\Form\FormStateInterface;
 | |
| use Drupal\flag\Plugin\Flag\EntityFlagType;
 | |
| use Drupal\Core\Cache\Cache;
 | |
| use Drupal\node\NodeInterface;
 | |
| use Drupal\Core\Entity\EntityInterface;
 | |
| use Drupal\Core\Entity\Display\EntityViewDisplayInterface;
 | |
| use Drupal\Core\Routing\RouteMatchInterface;
 | |
| use Drupal\system\Entity\Action;
 | |
| use Drupal\user\UserInterface;
 | |
| use Drupal\flag\FlagInterface;
 | |
| use Drupal\Core\Url;
 | |
| 
 | |
| /**
 | |
|  * Implements hook_help().
 | |
|  */
 | |
| function flag_help($route_name, RouteMatchInterface $route_match) {
 | |
|   switch ($route_name) {
 | |
|     case 'entity.flag.collection':
 | |
|       $output = '<p>' . t('This page lists all the <em>flags</em> that are currently defined on this system.') . '</p>';
 | |
|       if (\Drupal::moduleHandler()->moduleExists('views')) {
 | |
|         $output .= '<p>';
 | |
|         $output .= t('Lists of flagged content can be displayed using views. You can configure these in the Views administration section.');
 | |
|         if (\Drupal::service('flag')->getFlagById('bookmark')) {
 | |
|           $output .= ' ' . t('Flag module automatically provides a few default views for the <em>bookmarks</em> flag. You can use these as templates by cloning these views and then customizing as desired.');
 | |
|         }
 | |
|         $output .= ' ' . t('The <a href="@flag-handbook-url">Flag module handbook</a> contains extensive <a href="@customize-url">documentation on creating customized views</a> using flags.', ['@flag-handbook-url' => 'http://drupal.org/handbook/modules/flag', '@customize-url' => 'http://drupal.org/node/296954']);
 | |
|         $output .= '</p>';
 | |
|       }
 | |
| 
 | |
|       if (\Drupal::moduleHandler()->moduleExists('rules')) {
 | |
|         $output .= '<p>' . t('Flagging an item may trigger <a href="@rules-url">rules</a>.', ['@rules-url' => Url::fromRoute('entity.rules_reaction_rule.collection')->toString()]) . '</p>';
 | |
|       }
 | |
|       else {
 | |
|         $output .= '<p>' . t('Flagging an item may trigger <em>rules</em>. However, you don\'t have the <a href="@rules-url">Rules</a> module enabled, so you won\'t be able to enjoy this feature. The Rules module is a more extensive solution than Flag actions.', ['@rules-url' => Url::fromUri('http://drupal.org/node/407070')->toString()]) . '</p>';
 | |
|       }
 | |
| 
 | |
|       $output .= '<p>' . t('To learn about the various ways to use flags, please check out the <a href="@handbook-url">Flag module handbook</a>.', ['@handbook-url' => 'http://drupal.org/handbook/modules/flag']) . '</p>';
 | |
|       return $output;
 | |
| 
 | |
|     case 'flag.add_page':
 | |
|       $output = '<p>' . t('Select the type of flag to create.') . '</p>';
 | |
|       return $output;
 | |
| 
 | |
|     case 'field_ui.overview_flagging':
 | |
|       // @todo: Doesn't make sense at the moment, implement when form
 | |
|       // functionality is available.
 | |
|       /*
 | |
|       // Get the existing link types that provide a flagging form.
 | |
|       $link_types = flag_get_link_types();
 | |
|       $form_link_types = array();
 | |
|       foreach (flag_get_link_types() as $link_type) {
 | |
|         if ($link_type['provides form']) {
 | |
|           $form_link_types[] = '<em>' . $link_type['title'] . '</em>';
 | |
|         }
 | |
|       }
 | |
| 
 | |
|       // Get the flag for which we're managing fields.
 | |
|       $flag = menu_get_object('flag', FLAG_ADMIN_PATH_START + 1);
 | |
| 
 | |
|       // Common text.
 | |
|       $output  = '<p>' . t('Flags can have fields added to them. For example, a "Spam" flag could have a <em>Reason</em> field where a user could type in why he believes the item flagged is spam. A "Bookmarks" flag could have a <em>Folder</em> field into which a user could arrange her bookmarks.') . '</p>';
 | |
|       $output .= '<p>' . t('On this page you can add fields to flags, delete them, and otherwise manage them.') . '</p>';
 | |
| 
 | |
|       // Three cases:
 | |
|       if ($flag->link_type == 'form') {
 | |
|         // Case 1: the current link type is the flagging form. Don't tell the
 | |
|         // user anything extra, all is fine.
 | |
|       }
 | |
|       elseif ($link_types[$flag->link_type]['provides form']) {
 | |
|         // Case 2: the current link type shows the form for creation of the
 | |
|         // flagging, but it not the flagging form. Tell the user they can't edit
 | |
|         // existing flagging fields.
 | |
|         $output .= t("Field values may be edited when flaggings are created because this flag's link type shows a form for the flagging. However, to edit field values on existing flaggings, you will need to set your flag to use the <em>Flagging form</em> link type. This is provided by the <em><a href='!flagging-form-url'>Flagging Form</a></em> module.", array(
 | |
|           '!flagging-form-url' => 'http://drupal.org/project/flagging_form',
 | |
|         ));
 | |
|         if (!\Drupal::moduleHandler()->moduleExists('flagging_form')) {
 | |
|           $output .= ' <span class="warning">'
 | |
|             . t("You do not currently have this module enabled.")
 | |
|             . '</span>';
 | |
|         }
 | |
|         $output .= '</p>';
 | |
|       }
 | |
|       else {
 | |
|         // Case 3: the current link type does not allow access to the flagging
 | |
|         // form. Tell the user they should change it.
 | |
|         $output .= '<p class="warning">' . t("To allow users to enter values for fields you will need to <a href='!form-link-type-url'>set your flag</a> to use one of the following link types which allow users to access the flagging form: !link-types-list. (In case a form isn't used, the fields are assigned their default values.)", array(
 | |
|           '!form-link-type-url' => url('admin/structure/flags/manage/' . $flag->name, array('fragment' => 'edit-link-type')),
 | |
|           // The list of labels from link types. These are all defined in code
 | |
|           // in hook_flag_link_type_info() and therefore safe to output raw.
 | |
|           '!link-types-list' => implode(', ', $form_link_types),
 | |
|         )) . '</p>';
 | |
|         $output .= '<p>' . t("Additionally, to edit field values on existing flaggings, you will need to set your flag to use the Flagging form link type. This is provided by the <em><a href='!flagging-form-url'>Flagging Form</a></em> module.", array(
 | |
|           '!flagging-form-url' => 'http://drupal.org/project/flagging_form',
 | |
|         ));
 | |
|         if (!\Drupal::moduleHandler()->moduleExists('flagging_form')) {
 | |
|           $output .= ' <span class="warning">'
 | |
|             . t("You do not currently have this module enabled.")
 | |
|             . '</span>';
 | |
|         }
 | |
|         $output .= '</p>';
 | |
|       }
 | |
| 
 | |
|       return $output;
 | |
|       */
 | |
|   }
 | |
| }
 | |
| 
 | |
| /**
 | |
|  * Implements hook_form_alter().
 | |
|  */
 | |
| function flag_form_alter(&$form, FormStateInterface $form_state, $form_id) {
 | |
|   $object = $form_state->getFormObject();
 | |
| 
 | |
|   // We only want to operate on content entity forms.
 | |
|   if (!($object instanceof ContentEntityFormInterface) || ($object instanceof ConfirmFormInterface)) {
 | |
|     return;
 | |
|   }
 | |
| 
 | |
|   // Get the flags for the entity being edited by the form.
 | |
|   $flag_service = \Drupal::service('flag');
 | |
|   $entity = $object->getEntity();
 | |
|   $flags = $flag_service->getAllFlags($entity->getEntityTypeId(), $entity->bundle());
 | |
| 
 | |
|   // Check the first flag and return early if the form isn't considered to be
 | |
|   // an edit form.
 | |
|   if (!empty($flags) && isset($flags[0]) && $flags[0] instanceof FlagInterface) {
 | |
|     if (!$flags[0]->getFlagTypePlugin()->isAddEditForm($object->getOperation())) {
 | |
|       return;
 | |
|     }
 | |
|   }
 | |
| 
 | |
|   // Filter the flags to those that apply here:
 | |
|   //  - the flag uses the entity type plugin.
 | |
|   //  - the plugin is configured to output the flag in the entity form.
 | |
|   //  - the current user has access to the flag.
 | |
|   $filtered_flags = array_filter($flags, function(FlagInterface $flag) use ($object) {
 | |
|     $plugin = $flag->getFlagTypePlugin();
 | |
|     $entity = $object->getEntity();
 | |
|     $action = $flag->isFlagged($entity) ? 'unflag' : 'flag';
 | |
|     $access = $flag->actionAccess($action, NULL, $entity);
 | |
| 
 | |
|     return ($plugin instanceof EntityFlagType)
 | |
|       && $plugin->showOnForm()
 | |
|       && $access->isAllowed();
 | |
|   });
 | |
| 
 | |
|   // If we still have any flags...
 | |
|   if (!empty($filtered_flags)) {
 | |
| 
 | |
|     // Add a container to the form.
 | |
|     $form['flag'] = [
 | |
|       '#type' => 'details',
 | |
|       '#title' => t('Flags'),
 | |
|       '#attached' => ['library' => ['flag/flag.admin']],
 | |
|       '#group' => 'advanced',
 | |
|       '#tree' => TRUE,
 | |
|     ];
 | |
| 
 | |
|     /** @var FlagInterface $flag */
 | |
|     foreach ($filtered_flags as $flag) {
 | |
|       // Add each flag to the form.
 | |
|       $form['flag'][$flag->id()] = [
 | |
|         '#type' => 'checkbox',
 | |
|         '#title' => $flag->label(),
 | |
|         '#description' => $flag->getLongText('flag'),
 | |
|         '#default_value' => $flag->isFlagged($entity) ? 1 : 0,
 | |
|         '#return_value' => 1,
 | |
|         // Used by our drupalSetSummary() on vertical tabs.
 | |
|         '#attributes' => ['title' => $flag->label()],
 | |
|       ];
 | |
|     }
 | |
| 
 | |
|     foreach (array_keys($form['actions']) as $action) {
 | |
|       if ($action != 'preview' && isset($form['actions'][$action]['#type']) && $form['actions'][$action]['#type'] === 'submit') {
 | |
|         $form['actions'][$action]['#submit'][] = 'flag_form_submit';
 | |
|       }
 | |
|     }
 | |
|   }
 | |
| }
 | |
| 
 | |
| /**
 | |
|  * Form submission handler for the flag module.
 | |
|  *
 | |
|  * @see flag_form_alter()
 | |
|  */
 | |
| function flag_form_submit($form, FormStateInterface $form_state) {
 | |
|   $entity = $form_state->getFormObject()->getEntity();
 | |
|   if (!$form_state->isValueEmpty('flag')) {
 | |
|     $values = $form_state->getValue('flag');
 | |
|     flag_form_save($entity, $values);
 | |
|   }
 | |
| }
 | |
| 
 | |
| /**
 | |
|  * Performs flagging/unflagging for the entity edit form.
 | |
|  *
 | |
|  * @param \Drupal\Core\Entity\EntityInterface $entity
 | |
|  *   The entity being saved.
 | |
|  * @param $values
 | |
|  *   The flag entity form values.
 | |
|  *
 | |
|  * @see flag_form_submit()
 | |
|  */
 | |
| function flag_form_save(EntityInterface $entity, $values) {
 | |
|   $flag_service = \Drupal::service('flag');
 | |
|   $account = \Drupal::currentUser();
 | |
| 
 | |
|   // For existing entities, get any existing flaggings per flag.
 | |
|   $flagging_ids = [];
 | |
|   if (!$entity->isNew()) {
 | |
|     $flaggings = $flag_service->getAllEntityFlaggings($entity, $account);
 | |
|     $flagging_ids = array_map(function ($flagging) {
 | |
|       return $flagging->getFlagId();
 | |
|     }, $flaggings);
 | |
|   }
 | |
| 
 | |
|   // Load all the flags for the entity.
 | |
|   $flags = $flag_service->getAllFlags($entity->getEntityTypeId(), $entity->bundle());
 | |
| 
 | |
|   /** @var FlagInterface $flag */
 | |
|   foreach ($flags as $flag) {
 | |
|     // Get the flag_id from the Flag.
 | |
|     $flag_id = $flag->id();
 | |
| 
 | |
|     // If the flag_id is not part of the form values, no need to do anything.
 | |
|     if (!isset($values[$flag_id])) {
 | |
|       continue;
 | |
|     }
 | |
| 
 | |
|     // Get the form flag value.
 | |
|     $value = $values[$flag_id];
 | |
| 
 | |
|     // Determine if the flagging exists.
 | |
|     $flagging_exists = in_array($flag_id, $flagging_ids);
 | |
| 
 | |
|     // If the flag is checked in the form, and the flagging doesn't exist...
 | |
|     if ($value && !$flagging_exists) {
 | |
|       // ...flag the entity.
 | |
|       $flag_service->flag($flag, $entity);
 | |
|     }
 | |
| 
 | |
|     // If the flag is not checked in the form, and the flagging exists..
 | |
|     if (!$value && $flagging_exists) {
 | |
|       // ...unflag the entity.
 | |
|       $flag_service->unflag($flag, $entity);
 | |
|     }
 | |
|   }
 | |
| }
 | |
| 
 | |
| /**
 | |
|  * Implements hook_entity_extra_field_info().
 | |
|  */
 | |
| function flag_entity_extra_field_info() {
 | |
|   $extra = [];
 | |
|   $flag_service = \Drupal::service('flag');
 | |
|   $flags = $flag_service->getAllFlags();
 | |
| 
 | |
|   /** @var FlagInterface $flag */
 | |
|   foreach ($flags as $flag) {
 | |
|     // Skip flags that aren't on entities.
 | |
|     $flag_type_plugin = $flag->getFlagTypePlugin();
 | |
|     if (!($flag_type_plugin instanceof EntityFlagType)) {
 | |
|       continue;
 | |
|     }
 | |
| 
 | |
|     $flaggable_bundles = $flag->getApplicableBundles();
 | |
| 
 | |
|     foreach ($flaggable_bundles as $bundle_name) {
 | |
|       if ($flag_type_plugin->showOnForm()) {
 | |
|         $extra[$flag->getFlaggableEntityTypeId()][$bundle_name]['form']['flag'] = [
 | |
|           'label' => t('Flags'),
 | |
|           'description' => t('Checkboxes for toggling flags'),
 | |
|           'weight' => 10,
 | |
|         ];
 | |
|       }
 | |
| 
 | |
|       if ($flag_type_plugin->showAsField()) {
 | |
|         $extra[$flag->getFlaggableEntityTypeId()][$bundle_name]['display']['flag_' . $flag->id()] = [
 | |
|           'label' => t('Flag: %title', [
 | |
|             '%title' => $flag->label(),
 | |
|           ]),
 | |
|           'description' => t('Individual flag link'),
 | |
|           'weight' => 10,
 | |
|         ];
 | |
|       }
 | |
|     }
 | |
|   }
 | |
| 
 | |
|   return $extra;
 | |
| }
 | |
| 
 | |
| /**
 | |
|  * Implements hook_theme().
 | |
|  */
 | |
| function flag_theme() {
 | |
|   return [
 | |
|     'flag' => [
 | |
|       'variables' => [
 | |
|         'attributes' => [],
 | |
|         'title' => NULL,
 | |
|         'action' => 'flag',
 | |
|         'flag' => NULL,
 | |
|         'flaggable' => NULL,
 | |
|       ],
 | |
|     ],
 | |
|   ];
 | |
| }
 | |
| 
 | |
| /**
 | |
|  * Implements hook_theme_suggestions_HOOK().
 | |
|  */
 | |
| function flag_theme_suggestions_flag(array $variables) {
 | |
|   $flag = $variables['flag'];
 | |
|   $flaggable = $variables['flaggable'];
 | |
| 
 | |
|   return [
 | |
|     'flag__' . $flag->id(),
 | |
|     'flag__' . $flag->id() . '_' . $flaggable->id(),
 | |
|   ];
 | |
| }
 | |
| 
 | |
| /**
 | |
|  * Implements hook_node_links_alter().
 | |
|  */
 | |
| function flag_node_links_alter(array &$links, NodeInterface $entity, array &$context) {
 | |
|   // @todo: Define this for handling the showOnLinks() flag mode.
 | |
|   // see https://www.drupal.org/project/flag/issues/2703229
 | |
| }
 | |
| 
 | |
| /**
 | |
|  * Implements hook_entity_view().
 | |
|  *
 | |
|  * Handles the 'show_in_links' and 'show_as_field' flag options.
 | |
|  */
 | |
| function flag_entity_view(array &$build, EntityInterface $entity, EntityViewDisplayInterface $display, $view_mode) {
 | |
|   // Don't show on previews.
 | |
|   if ($entity->isNew()) {
 | |
|     return;
 | |
|   }
 | |
| 
 | |
|   $build['#cache']['contexts'][] = 'user.permissions';
 | |
| 
 | |
|   if (empty($build['#cache']['tags'])) {
 | |
|     $build['#cache']['tags'] = [];
 | |
|   }
 | |
| 
 | |
|   // Get all possible flags for this entity type.
 | |
|   $flag_service = \Drupal::service('flag');
 | |
|   $flags = $flag_service->getAllFlags($entity->getEntityTypeID(), $entity->bundle());
 | |
| 
 | |
|   foreach ($flags as $flag) {
 | |
|     $build['#cache']['tags'] = Cache::mergeTags($build['#cache']['tags'], $flag->getCacheTags());
 | |
| 
 | |
|     // Do not display the flag if disabled.
 | |
|     if (!$flag->status()){
 | |
|       continue;
 | |
|     }
 | |
| 
 | |
|     $flag_type_plugin = $flag->getFlagTypePlugin();
 | |
| 
 | |
|     // Only add cache key if flag link is displayed.
 | |
|     if (!$flag_type_plugin->showAsField() || !$display->getComponent('flag_' . $flag->id())) {
 | |
|       continue;
 | |
|     }
 | |
| 
 | |
|     $build['flag_' . $flag->id()] = [
 | |
|       '#lazy_builder' => ['flag.link_builder:build', [
 | |
|         $entity->getEntityTypeId(),
 | |
|         $entity->id(),
 | |
|         $flag->id(),
 | |
|       ]],
 | |
|       '#create_placeholder' => TRUE,
 | |
|     ];
 | |
|   }
 | |
| }
 | |
| 
 | |
| /**
 | |
|  * Implements hook_entity_build_defaults_alter().
 | |
|  */
 | |
| function flag_entity_build_defaults_alter(array &$build, EntityInterface $entity, $view_mode = 'full', $langcode = NULL) {
 | |
|   /** @var \Drupal\flag\FlagService $flag_service */
 | |
|   $flag_service = \Drupal::service('flag');
 | |
| 
 | |
|   // Get all possible flags for this entity type.
 | |
|   $flags = $flag_service->getAllFlags($entity->getEntityTypeId(), $entity->bundle());
 | |
| 
 | |
|   $no_cache = FALSE;
 | |
|   foreach ($flags as $flag) {
 | |
|     $flag_type_plugin = $flag->getFlagTypePlugin();
 | |
| 
 | |
|     // Make sure we're dealing with an entity flag type.
 | |
|     if (!$flag_type_plugin instanceof EntityFlagType) {
 | |
|       continue;
 | |
|     }
 | |
| 
 | |
|     // Only add max-age to entity render array if contextual links flag
 | |
|     // display is enabled.
 | |
|     if (!$flag_type_plugin->showContextualLink()) {
 | |
|       continue;
 | |
|     }
 | |
| 
 | |
|     $no_cache = TRUE;
 | |
|   }
 | |
| 
 | |
|   if ($no_cache) {
 | |
|     $build['#cache']['max-age'] = 0;
 | |
|   }
 | |
| 
 | |
|   return $build;
 | |
| }
 | |
| 
 | |
| /**
 | |
|  * Implements hook_entity_view_alter().
 | |
|  *
 | |
|  * Alters node contextual links placeholder id to contain flag metadata, so that
 | |
|  * contextual links cache considers flags granularity.
 | |
|  */
 | |
| function flag_entity_view_alter(&$build, EntityInterface $entity, EntityViewDisplayInterface $display) {
 | |
|   $entity_type = $entity->getEntityTypeId();
 | |
|   if (isset($build['#contextual_links'][$entity_type])) {
 | |
|     /** @var \Drupal\flag\FlagService $flag_service */
 | |
|     $flag_service = \Drupal::service('flag');
 | |
| 
 | |
|     // Get all possible flags for this entity type.
 | |
|     $flags = $flag_service->getAllFlags($entity_type, $entity->bundle());
 | |
| 
 | |
|     foreach ($flags as $flag) {
 | |
|       $flag_type_plugin = $flag->getFlagTypePlugin();
 | |
| 
 | |
|       // Make sure we're dealing with an entity flag type.
 | |
|       if (!$flag_type_plugin instanceof EntityFlagType) {
 | |
|         continue;
 | |
|       }
 | |
| 
 | |
|       // Only apply metadata to contextual links if plugin is enabled
 | |
|       if (!$flag_type_plugin->showContextualLink()) {
 | |
|         continue;
 | |
|       }
 | |
| 
 | |
|       $action = 'flag';
 | |
|       if ($flag->isFlagged($entity)) {
 | |
|         $action = 'unflag';
 | |
|       }
 | |
| 
 | |
|       $flag_keys[] = $flag->id() . '-' . $action;
 | |
|     }
 | |
| 
 | |
|     if (!empty($flag_keys)) {
 | |
|       $build['#contextual_links'][$entity_type]['metadata']['flag_keys'] = implode(',', $flag_keys);
 | |
|     }
 | |
|   }
 | |
| }
 | |
| 
 | |
| /**
 | |
|  * Implements hook_contextual_links_alter().
 | |
|  */
 | |
| function flag_contextual_links_alter(array &$links, $group, array $route_parameters) {
 | |
|   // Assume that $group is one of known entity types and try to load an entity
 | |
|   // based on that.
 | |
|   $entity_type = $group;
 | |
|   if (isset($route_parameters[$entity_type]) && !is_null(\Drupal::entityTypeManager()->getDefinition($entity_type, FALSE))) {
 | |
|     $entity = \Drupal::entityTypeManager()->getStorage($entity_type)->load($route_parameters[$entity_type]);
 | |
|   }
 | |
| 
 | |
|   if (!isset($entity)) {
 | |
|     return;
 | |
|   }
 | |
| 
 | |
|   // Get all possible flags for this entity type.
 | |
|   $flag_service = \Drupal::service('flag');
 | |
|   $flags = $flag_service->getAllFlags($entity->getEntityTypeID(), $entity->bundle());
 | |
| 
 | |
|   foreach ($flags as $flag) {
 | |
|     /** @var \Drupal\flag\FlagInterface $flag */
 | |
|     // Do not display the flag if disabled.
 | |
|     if (!$flag->status()){
 | |
|       continue;
 | |
|     }
 | |
| 
 | |
|     /** @var \Drupal\flag\Plugin\Flag\EntityFlagType $flag_type_plugin */
 | |
|     $flag_type_plugin = $flag->getFlagTypePlugin();
 | |
| 
 | |
|     // Make sure we're dealing with an entity flag type.
 | |
|     if (!$flag_type_plugin instanceof EntityFlagType) {
 | |
|       continue;
 | |
|     }
 | |
| 
 | |
|     // Skip flags for which contextual links setting is disabled.
 | |
|     if (!$flag_type_plugin->showContextualLink()) {
 | |
|       continue;
 | |
|     }
 | |
| 
 | |
|     $flag_link = $flag
 | |
|       ->getLinkTypePlugin()
 | |
|       ->getAsLink($flag, $entity);
 | |
| 
 | |
|     $flag_url = $flag_link->getUrl();
 | |
| 
 | |
|     $links["flag_{$flag->id()}"] = [
 | |
|       'route_name' => $flag_url->getRouteName(),
 | |
|       'route_parameters' => $flag_url->getRouteParameters(),
 | |
|       'title' => $flag_link->getText(),
 | |
|       'localized_options' => [],
 | |
|     ];
 | |
|   }
 | |
| }
 | |
| 
 | |
| /*
 | |
|  * Implements hook_entity_predelete().
 | |
|  */
 | |
| function flag_entity_predelete(EntityInterface $entity) {
 | |
|   // User flags handle things through user entity hooks.
 | |
|   if ($entity->getEntityTypeId() == 'user') {
 | |
|     return;
 | |
|   }
 | |
| 
 | |
|   \Drupal::service('flag')->unflagAllByEntity($entity);
 | |
| }
 | |
| 
 | |
| /**
 | |
|  * Implements hook_user_cancel().
 | |
|  */
 | |
| function flag_user_cancel($edit, $account, $method) {
 | |
|   \Drupal::service('flag')->userFlagRemoval($account);
 | |
| }
 | |
| 
 | |
| /**
 | |
|  * Implements hook_user_predelete().
 | |
|  */
 | |
| function flag_user_predelete(UserInterface $account) {
 | |
|   \Drupal::service('flag')->userFlagRemoval($account);
 | |
| }
 | |
| 
 | |
| /**
 | |
|  * Implements hook_entity_operation().
 | |
|  */
 | |
| function flag_entity_operation(\Drupal\Core\Entity\EntityInterface $entity) {
 | |
|   $operations = [];
 | |
| 
 | |
|   if ($entity instanceof \Drupal\flag\FlagInterface) {
 | |
|     if (!$entity->status()) {
 | |
|       $operations['enable'] = [
 | |
|         'title' => t('Enable'),
 | |
|         'url' => $entity->toUrl('enable'),
 | |
|         'weight' => 50,
 | |
|       ];
 | |
|     }
 | |
|     else {
 | |
|       $operations['disable'] = [
 | |
|         'title' => t('Disable'),
 | |
|         'url' => $entity->toUrl('disable'),
 | |
|         'weight' => 50,
 | |
|       ];
 | |
|     }
 | |
| 
 | |
|     $operations['reset'] = [
 | |
|       'title' => t('Reset'),
 | |
|       'url' => $entity->toUrl('reset'),
 | |
|       'weight' => 100,
 | |
|     ];
 | |
|   }
 | |
| 
 | |
|   return $operations;
 | |
| }
 | |
| 
 | |
| /**
 | |
|  * Implements hook_hook_info().
 | |
|  *
 | |
|  * Flag alter hooks should be defined in a MODULE.flag.inc file.
 | |
|  */
 | |
| function flag_hook_info() {
 | |
|   $hooks = [];
 | |
| 
 | |
|   $hooks['flag_type_info_alter'] = [
 | |
|     'group' => 'flag',
 | |
|   ];
 | |
|   $hooks['flag_link_type_info_alter'] = [
 | |
|     'group' => 'flag',
 | |
|   ];
 | |
| 
 | |
|   return $hooks;
 | |
| }
 | |
| 
 | |
| /**
 | |
|  * Implements hook_ENTITY_TYPE_insert().
 | |
|  */
 | |
| function flag_flag_insert(FlagInterface $flag) {
 | |
|   if ($flag->isSyncing()) {
 | |
|     // Do not create actions when config is progress of synchronization.
 | |
|     return;
 | |
|   }
 | |
|   // The action plugin cache needs to detect the new flag.
 | |
|   /** @var \Drupal\Core\Action\ActionManager $action_manager */
 | |
|   $action_manager = \Drupal::service('plugin.manager.action');
 | |
|   $action_manager->clearCachedDefinitions();
 | |
| 
 | |
|   // Add the flag/unflag actions for this flag and entity combination.
 | |
|   $flag_id = 'flag_action.' . $flag->id() . '_flag';
 | |
|   if (!Action::load($flag_id)) {
 | |
|     $action = Action::create([
 | |
|       'id' => $flag_id,
 | |
|       'type' => $flag->getFlaggableEntityTypeId(),
 | |
|       'label' => $flag->getShortText('flag'),
 | |
|       'plugin' => 'flag_action:' . $flag->id() . '_flag',
 | |
|       'configuration' => [
 | |
|         'flag_id' => $flag->id(),
 | |
|         'flag_action' => 'flag',
 | |
|       ],
 | |
|     ]);
 | |
|     $action->trustData()->save();
 | |
|   }
 | |
|   $unflag_id = 'flag_action.' . $flag->id() . '_unflag';
 | |
|   if (!Action::load($unflag_id)) {
 | |
|     $action = Action::create([
 | |
|       'id' => $unflag_id,
 | |
|       'type' => $flag->getFlaggableEntityTypeId(),
 | |
|       'label' => $flag->getShortText('unflag'),
 | |
|       'plugin' => 'flag_action:' . $flag->id() . '_unflag',
 | |
|       'configuration' => [
 | |
|         'flag_id' => $flag->id(),
 | |
|         'flag_action' => 'unflag',
 | |
|       ],
 | |
|     ]);
 | |
|     $action->trustData()->save();
 | |
|   }
 | |
| }
 | |
| 
 | |
| /**
 | |
|  * Implements hook_ENTITY_TYPE_delete().
 | |
|  */
 | |
| function flag_flag_delete(FlagInterface $flag) {
 | |
|   // Do not delete actions when config is progress of synchronization.
 | |
|   if ($flag->isSyncing()) {
 | |
|     return;
 | |
|   }
 | |
| 
 | |
|   $actions = Action::loadMultiple([
 | |
|     'flag_action.' . $flag->id() . '_flag',
 | |
|     'flag_action.' . $flag->id() . '_unflag',
 | |
|   ]);
 | |
| 
 | |
|   // Remove the flag/unflag actions for this flag and entity combination.
 | |
|   foreach ($actions as $action) {
 | |
|     $action->delete();
 | |
|   }
 | |
| }
 |