diff --git a/core/modules/media_library/src/Form/FileUploadForm.php b/core/modules/media_library/src/Form/FileUploadForm.php
index cfc85651e0..81367821c2 100644
--- a/core/modules/media_library/src/Form/FileUploadForm.php
+++ b/core/modules/media_library/src/Form/FileUploadForm.php
@@ -14,6 +14,7 @@
 use Drupal\Core\Render\RendererInterface;
 use Drupal\Core\Url;
 use Drupal\file\FileInterface;
+use Drupal\file\FileUsage\FileUsageInterface;
 use Drupal\file\Plugin\Field\FieldType\FileFieldItemList;
 use Drupal\file\Plugin\Field\FieldType\FileItem;
 use Drupal\media\MediaInterface;
@@ -53,6 +54,13 @@ class FileUploadForm extends AddFormBase {
    */
   protected $fileSystem;
 
+  /**
+   * The file usage service.
+   *
+   * @var \Drupal\file\FileUsage\FileUsageInterface
+   */
+  protected $fileUsage;
+
   /**
    * Constructs a new FileUploadForm.
    *
@@ -68,12 +76,19 @@ class FileUploadForm extends AddFormBase {
    *   The file system service.
    * @param \Drupal\media_library\OpenerResolverInterface $opener_resolver
    *   The opener resolver.
+   * @param \Drupal\file\FileUsage\FileUsageInterface $file_usage
+   *   The file usage service.
    */
-  public function __construct(EntityTypeManagerInterface $entity_type_manager, MediaLibraryUiBuilder $library_ui_builder, ElementInfoManagerInterface $element_info, RendererInterface $renderer, FileSystemInterface $file_system, OpenerResolverInterface $opener_resolver = NULL) {
+  public function __construct(EntityTypeManagerInterface $entity_type_manager, MediaLibraryUiBuilder $library_ui_builder, ElementInfoManagerInterface $element_info, RendererInterface $renderer, FileSystemInterface $file_system, OpenerResolverInterface $opener_resolver = NULL, FileUsageInterface $file_usage = NULL) {
     parent::__construct($entity_type_manager, $library_ui_builder, $opener_resolver);
     $this->elementInfo = $element_info;
     $this->renderer = $renderer;
     $this->fileSystem = $file_system;
+    if (!$file_usage) {
+      @trigger_error('Calling FileUploadForm::__construct() without the `file.usage` service is deprecated in drupal:8.8.0 and is removed in drupal:9.0.0. Pass the `file.usage` service to the constructor. See https://www.drupal.org/node/3075165', E_USER_DEPRECATED);
+      $file_usage = \Drupal::service('file.usage');
+    }
+    $this->fileUsage = $file_usage;
   }
 
   /**
@@ -86,7 +101,8 @@ public static function create(ContainerInterface $container) {
       $container->get('element_info'),
       $container->get('renderer'),
       $container->get('file_system'),
-      $container->get('media_library.opener_resolver')
+      $container->get('media_library.opener_resolver'),
+      $container->get('file.usage')
     );
   }
 
@@ -290,4 +306,29 @@ protected function prepareMediaEntityForSave(MediaInterface $media) {
     $file->save();
   }
 
+  /**
+   * Submit handler for the remove button.
+   *
+   * @param array $form
+   *   The form render array.
+   * @param \Drupal\Core\Form\FormStateInterface $form_state
+   *   The form state.
+   */
+  public function removeButtonSubmit(array $form, FormStateInterface $form_state) {
+    // Retrieve the delta of the media item from the parents of the remove
+    // button.
+    $triggering_element = $form_state->getTriggeringElement();
+    $delta = array_slice($triggering_element['#array_parents'], -2, 1)[0];
+
+    /** @var \Drupal\media\MediaInterface $removed_media */
+    $removed_media = $form_state->get(['media', $delta]);
+
+    $file = $removed_media->get($this->getSourceFieldName($removed_media->bundle->entity))->entity;
+    if ($file instanceof FileInterface && empty($this->fileUsage->listUsage($file))) {
+      $file->delete();
+    }
+
+    parent::removeButtonSubmit($form, $form_state);
+  }
+
 }
diff --git a/core/modules/media_library/tests/src/FunctionalJavascript/MediaLibraryTest.php b/core/modules/media_library/tests/src/FunctionalJavascript/MediaLibraryTest.php
index 180c6fa209..a088e87678 100644
--- a/core/modules/media_library/tests/src/FunctionalJavascript/MediaLibraryTest.php
+++ b/core/modules/media_library/tests/src/FunctionalJavascript/MediaLibraryTest.php
@@ -237,8 +237,8 @@ public function testWidgetWithoutMediaTypes() {
     $field_empty_types_message = 'There are no allowed media types configured for this field. <a href="' . $field_empty_types_url->toString() . '">Edit the field settings</a> to select the allowed media types.';
 
     $field_null_types_url = new Url('entity.field_config.node_field_edit_form', [
-        'field_config' => 'node.basic_page.field_null_types_media',
-      ] + $route_bundle_params);
+      'field_config' => 'node.basic_page.field_null_types_media',
+    ] + $route_bundle_params);
     $field_null_types_message = 'There are no allowed media types configured for this field. <a href="' . $field_null_types_url->toString() . '">Edit the field settings</a> to select the allowed media types.';
 
     // Visit a node create page.
@@ -1092,8 +1092,7 @@ public function testWidgetUpload() {
     // Assert the name field contains the filename and the alt text is required.
     $assert_session->fieldValueEquals('Name', $png_image->filename);
     $assert_session->elementExists('css', '.ui-dialog-buttonpane')->pressButton('Save and select');
-    $assert_session->assertWaitOnAjaxRequest();
-    $assert_session->pageTextContains('Alternative text field is required');
+    $this->assertNotEmpty($assert_session->waitForText('Alternative text field is required'));
     $page->fillField('Alternative text', $this->randomString());
     $assert_session->elementExists('css', '.ui-dialog-buttonpane')->pressButton('Save and select');
     $assert_session->assertWaitOnAjaxRequest();
@@ -1115,26 +1114,26 @@ public function testWidgetUpload() {
     $assert_session->pageTextContains('1 of 2 items selected');
     $assert_session->hiddenFieldValueEquals('current_selection', $added_media->id());
     // Ensure the created item is added in the widget.
+    $this->assertNotEmpty($assert_session->waitForText('Add or select media'));
     $assert_session->elementExists('css', '.ui-dialog-buttonpane')->pressButton('Insert selected');
     $this->assertNotEmpty($assert_session->waitForText('Added one media item.'));
-    $assert_session->assertWaitOnAjaxRequest();
     $assert_session->pageTextNotContains('Add or select media');
     $assert_session->pageTextContains($png_image->filename);
 
     // Remove the item.
     $assert_session->elementExists('css', '.media-library-item__remove')->click();
-    $assert_session->assertWaitOnAjaxRequest();
+    $this->assertNotEmpty($assert_session->waitForElementRemoved('css', '.media-library-item'));
     $assert_session->pageTextNotContains($png_image->filename);
 
     // Assert we can also directly insert uploaded files in the widget.
     $assert_session->elementExists('css', '.media-library-open-button[name^="field_twin_media"]')->click();
     $assert_session->assertWaitOnAjaxRequest();
-    $assert_session->pageTextContains('Add or select media');
+    $this->assertNotEmpty($assert_session->waitForText('Add or select media'));
     $page->clickLink('Type Three');
     $assert_session->assertWaitOnAjaxRequest();
     $png_uri_2 = $file_system->copy($png_image->uri, 'public://');
     $page->attachFileToField('Add files', $this->container->get('file_system')->realpath($png_uri_2));
-    $assert_session->assertWaitOnAjaxRequest();
+    $this->assertNotEmpty($assert_session->waitforButton('Remove'));
     $page->fillField('Alternative text', $this->randomString());
     $assert_session->elementExists('css', '.ui-dialog-buttonpane')->pressButton('Save and insert');
     $this->assertNotEmpty($assert_session->waitForText('Added one media item.'));
@@ -1164,16 +1163,15 @@ public function testWidgetUpload() {
     $page->fillField('Name', 'Unlimited Cardinality Image');
     $page->fillField('Alternative text', $this->randomString());
     $assert_session->elementExists('css', '.ui-dialog-buttonpane')->pressButton('Save and select');
-    $assert_session->assertWaitOnAjaxRequest();
+    // Ensure the media item was saved to the library and automatically
+    // selected. The added media items should be in the first position of the
+    // add form.
     // Load the created media item.
+    $this->assertNotEmpty($assert_session->waitForText('Add or select media'));
+    $this->assertNotEmpty($assert_session->waitForText('Unlimited Cardinality Image'));
     $media_items = Media::loadMultiple();
     $added_media = array_pop($media_items);
     $added_media_name = $added_media->label();
-    // Ensure the media item was saved to the library and automatically
-    // selected. The added media items should be in the first position of the
-    // add form.
-    $assert_session->pageTextContains('Add or select media');
-    $assert_session->pageTextContains('Unlimited Cardinality Image');
     $assert_session->fieldValueEquals('media_library_select_form[0]', $added_media->id());
     $assert_session->checkboxChecked('media_library_select_form[0]');
     // Assert the item that was selected before uploading the file is still
@@ -1257,7 +1255,8 @@ public function testWidgetUpload() {
     // Assert the pre-selected items are shown.
     $selection_area = $assert_session->elementExists('css', '.media-library-add-form__selected-media');
     $assert_session->elementExists('css', 'summary', $selection_area)->click();
-    $assert_session->checkboxChecked("Select $existing_media_name", $selection_area);
+    $this->assertNotEmpty($checkbox = $assert_session->waitForField("Select $existing_media_name"));
+    $this->assertTrue($checkbox->isChecked());
     $page->uncheckField("Select $existing_media_name");
     $page->fillField('Alternative text', $this->randomString());
     $assert_session->hiddenFieldValueEquals('current_selection', '');
@@ -1321,7 +1320,7 @@ public function testWidgetUpload() {
     // Create a list of new files to upload.
     $filenames = [];
     $remote_paths = [];
-    foreach (range(1, 3) as $i) {
+    foreach (range(1, 4) as $i) {
       $path = $file_system->copy($png_image->uri, 'public://');
       $filenames[] = $file_system->basename($path);
       $remote_paths[] = $driver->uploadFileAndGetRemoteFilePath($file_system->realpath($path));
@@ -1336,19 +1335,51 @@ public function testWidgetUpload() {
     $assert_session->fieldValueEquals('media[0][fields][name][0][value]', $filenames[0]);
     $assert_session->fieldValueEquals('media[1][fields][name][0][value]', $filenames[1]);
     $assert_session->fieldValueEquals('media[2][fields][name][0][value]', $filenames[2]);
+    $assert_session->fieldValueEquals('media[3][fields][name][0][value]', $filenames[3]);
     // Assert the pre-selected items are shown.
-    $selection_area = $assert_session->elementExists('css', '.media-library-add-form__selected-media');
+    $this->assertNotEmpty($selection_area = $assert_session->waitForElement('css', '.media-library-add-form__selected-media'));
     $assert_session->elementExists('css', 'summary', $selection_area)->click();
     $assert_session->checkboxChecked("Select $existing_media_name", $selection_area);
-    // Set alt texts for items 1 and 2, leave the alt text empty for item 3 to
-    // assert the field validation does not stop users from removing items.
+    // Set alt texts for items 1 and 2, leave the alt text empty for items 3
+    // and 4 to assert the field validation does not stop users from removing
+    // items.
     $page->fillField('media[0][fields][field_media_test_image][0][alt]', $filenames[0]);
     $page->fillField('media[1][fields][field_media_test_image][0][alt]', $filenames[1]);
+    // Assert the file is available in the file storage.
+    $files = $file_storage->loadByProperties(['filename' => $filenames[1]]);
+    $this->assertCount(1, $files);
+    $file_1_uri = reset($files)->getFileUri();
     // Remove the second file and assert the focus is shifted to the container
     // of the next media item and field values are still correct.
     $page->pressButton('media-1-remove-button');
     $this->assertJsCondition('jQuery(".media-library-add-form__media[data-media-library-added-delta=2]").is(":focus")');
     $assert_session->pageTextContains('The media item ' . $filenames[1] . ' has been removed.');
+    // Assert the file was deleted.
+    $this->assertEmpty($file_storage->loadByProperties(['filename' => $filenames[1]]));
+    $this->assertFileNotExists($file_1_uri);
+
+    // When a file is already in usage, it should not be deleted. To test,
+    // let's add a usage for $filenames[3] (now in the third position).
+    $files = $file_storage->loadByProperties(['filename' => $filenames[3]]);
+    $target_file = reset($files);
+    $this->assertCount(1, $files);
+    Media::create([
+      'bundle' => 'type_three',
+      'name' => 'Disturbing',
+      'field_media_test_image' => [
+        ['target_id' => $target_file->id()],
+      ],
+    ])->save();
+    // Remove $filenames[3] (now in the third position) and assert the focus is
+    // shifted to the container of the previous media item and field values are
+    // still correct.
+    $page->pressButton('media-3-remove-button');
+    $this->assertTrue($assert_session->waitForText('The media item ' . $filenames[3] . ' has been removed.'));
+    $this->assertJsCondition('jQuery(".media-library-add-form__media[data-media-library-added-delta=2]").is(":focus")');
+    // Assert the file was not deleted, due to being in use elsewhere.
+    $this->assertNotEmpty($file_storage->loadByProperties(['filename' => $filenames[3]]));
+    $this->assertFileExists($target_file->getFileUri());
+
     // The second media item should be removed (this has the delta 1 since we
     // start counting from 0).
     $assert_session->elementNotExists('css', '.media-library-add-form__media[data-media-library-added-delta=1]');
