public static ManagedFile::processManagedFile(&$element, FormStateInterface $form_state, &$complete_form)
Render API callback: Expands the managed_file element type.
Expands the file type to include Upload and Remove buttons, as well as support for a default value.
File
- core/modules/file/src/Element/ManagedFile.php, line 206
Class
- ManagedFile
- Provides an AJAX/progress aware widget for uploading and saving a file.
Namespace
Drupal\file\Element
Code
public static function processManagedFile(&$element, FormStateInterface $form_state, &$complete_form) { // This is used sometimes so let's implode it just once. $parents_prefix = implode('_', $element['#parents']); $fids = isset($element['#value']['fids']) ? $element['#value']['fids'] : []; // Set some default element properties. $element['#progress_indicator'] = empty($element['#progress_indicator']) ? 'none' : $element['#progress_indicator']; $element['#files'] = !empty($fids) ? File::loadMultiple($fids) : FALSE; $element['#tree'] = TRUE; // Generate a unique wrapper HTML ID. $ajax_wrapper_id = Html::getUniqueId('ajax-wrapper'); $ajax_settings = [ 'callback' => [get_called_class(), 'uploadAjaxCallback'], 'options' => [ 'query' => [ 'element_parents' => implode('/', $element['#array_parents']), ], ], 'wrapper' => $ajax_wrapper_id, 'effect' => 'fade', 'progress' => [ 'type' => $element['#progress_indicator'], 'message' => $element['#progress_message'], ], ]; // Set up the buttons first since we need to check if they were clicked. $element['upload_button'] = [ '#name' => $parents_prefix . '_upload_button', '#type' => 'submit', '#value' => t('Upload'), '#attributes' => ['class' => ['js-hide']], '#validate' => [], '#submit' => ['file_managed_file_submit'], '#limit_validation_errors' => [$element['#parents']], '#ajax' => $ajax_settings, '#weight' => -5, ]; // Force the progress indicator for the remove button to be either 'none' or // 'throbber', even if the upload button is using something else. $ajax_settings['progress']['type'] = ($element['#progress_indicator'] == 'none') ? 'none' : 'throbber'; $ajax_settings['progress']['message'] = NULL; $ajax_settings['effect'] = 'none'; $element['remove_button'] = [ '#name' => $parents_prefix . '_remove_button', '#type' => 'submit', '#value' => $element['#multiple'] ? t('Remove selected') : t('Remove'), '#validate' => [], '#submit' => ['file_managed_file_submit'], '#limit_validation_errors' => [$element['#parents']], '#ajax' => $ajax_settings, '#weight' => 1, ]; $element['fids'] = [ '#type' => 'hidden', '#value' => $fids, ]; // Add progress bar support to the upload if possible. if ($element['#progress_indicator'] == 'bar' && $implementation = file_progress_implementation()) { $upload_progress_key = mt_rand(); if ($implementation == 'uploadprogress') { $element['UPLOAD_IDENTIFIER'] = [ '#type' => 'hidden', '#value' => $upload_progress_key, '#attributes' => ['class' => ['file-progress']], // Uploadprogress extension requires this field to be at the top of // the form. '#weight' => -20, ]; } elseif ($implementation == 'apc') { $element['APC_UPLOAD_PROGRESS'] = [ '#type' => 'hidden', '#value' => $upload_progress_key, '#attributes' => ['class' => ['file-progress']], // Uploadprogress extension requires this field to be at the top of // the form. '#weight' => -20, ]; } // Add the upload progress callback. $element['upload_button']['#ajax']['progress']['url'] = Url::fromRoute('file.ajax_progress', ['key' => $upload_progress_key]); } // The file upload field itself. $element['upload'] = [ '#name' => 'files[' . $parents_prefix . ']', '#type' => 'file', '#title' => t('Choose a file'), '#title_display' => 'invisible', '#size' => $element['#size'], '#multiple' => $element['#multiple'], '#theme_wrappers' => [], '#weight' => -10, '#error_no_message' => TRUE, ]; if (!empty($fids) && $element['#files']) { foreach ($element['#files'] as $delta => $file) { $file_link = [ '#theme' => 'file_link', '#file' => $file, ]; if ($element['#multiple']) { $element['file_' . $delta]['selected'] = [ '#type' => 'checkbox', '#title' => \Drupal::service('renderer')->renderPlain($file_link), ]; } else { $element['file_' . $delta]['filename'] = $file_link + ['#weight' => -10]; } // Anonymous users who have uploaded a temporary file need a // non-session-based token added so $this->valueCallback() can check // that they have permission to use this file on subsequent submissions // of the same form (for example, after an Ajax upload or form // validation error). if ($file->isTemporary() && \Drupal::currentUser()->isAnonymous()) { $element['file_' . $delta]['fid_token'] = array( '#type' => 'hidden', '#value' => Crypt::hmacBase64('file-' . $delta, \Drupal::service('private_key')->get() . Settings::getHashSalt()), ); } } } // Add the extension list to the page as JavaScript settings. if (isset($element['#upload_validators']['file_validate_extensions'][0])) { $extension_list = implode(',', array_filter(explode(' ', $element['#upload_validators']['file_validate_extensions'][0]))); $element['upload']['#attached']['drupalSettings']['file']['elements']['#' . $element['#id']] = $extension_list; } // Let #id point to the file element, so the field label's 'for' corresponds // with it. $element['#id'] = &$element['upload']['#id']; // Prefix and suffix used for Ajax replacement. $element['#prefix'] = '<div id="' . $ajax_wrapper_id . '">'; $element['#suffix'] = '</div>'; return $element; }
Please login to continue.