Подтвердить что ты не робот

Загрузка файлов с использованием поля input type="file" с событием .change() не всегда срабатывает в IE и Chrome

У меня есть простой кусок кода для загрузки файлов:

$(document).ready(function () {
    $(".attachmentsUpload input.file").change(function () {
        $('form').submit();
    });
});

<form class="attachmentsUpload" action="/UploadHandler.ashx" method="post" enctype="multipart/form-data">
    <input type="file" class="file" name="file" />
</form>

Пока я нажимаю на ввод, а затем выбираю файл в диалоговом окне, я отправляю этот файл с помощью ajax. Это не важная часть здесь. Важная часть состоит в том, что, когда я дважды выбираю тот же файл в диалоговом окне, сразу после отправки первого файла, событие .change() не срабатывает в IE и Chrome. Но, когда я выбираю другой файл, событие срабатывает и работает правильно. Под Firefox он все время стреляет.

Как обойти это, работать как ожидалось (как в Firefox)?

4b9b3361

Ответ 1

Описание

Это происходит потому, что значение поля ввода (выбранный путь к файлу) не изменяется, если вы снова выбираете тот же файл.

Вы можете установить значение в событии onChange() пустой строкой и отправить свою форму, только если значение не пустое. Посмотрите на мой образец и демонстрация jsFiddle.

Пример

$(".attachmentsUpload input.file").change(function () {
    if ($(".attachmentsUpload input.file").val() == "") {
        return;
    }
    // your ajax submit
    $(".attachmentsUpload input.file").val("");
});

Update

Это по какой-либо причине не работает в IE9. Вы можете заменить элемент на reset их. В этом случае вам нужно jQuery live(), чтобы связать событие, потому что ваше поле ввода будет динамически (повторно) создано. Это будет работать во всех браузерах.

Я нашел это решение в ответе stackoverflow Очистка input type='file' с помощью jQuery

$(".attachmentsUpload input.file").live("change", function () {
    if ($(".attachmentsUpload input.file").val() == "") {
        return;
    }
    // get the inputs value
    var fileInputContent = $(".attachmentsUpload input.file").val();
    // your ajax submit
    alert("submit value of the file input field=" + fileInputContent);
    // reset the field
    $(".attachmentsUpload input.file").replaceWith('<input type="file" class="file" name="file" />');
});​

Дополнительная информация

Ознакомьтесь с моим обновленным jsFiddle

Ответ 2

На основе ответа dknaack ключом является использование jquery live для привязки события изменения и сброса поля ввода после отправки:

$(document).ready(function () {
    $(".attachmentsUpload input.file").change(function () {
        $('form').submit();  /* sync submit */
        $(".attachmentsUpload input.file").replaceWith('<input type="file" class="file" name="file" />');
    });
});

Сброс должен выполняться после отправки. Когда submit async, reset поле, например, в событии ajax success.

$(document).ready(function () {
    $(".attachmentsUpload input.file").change(function () {
        $('form').submit();  /* async submit */
    });
});

.ajaxForm({
    ...
    success: function (result) {
        // reset the field - needed for IE to upload the same file second time                    
        $this.find("input.file").replaceWith('<input type="file" class="file" name="file" />');
    }
});

Ответ 3

Убедитесь, что ваш script завернут в оболочку $(function() {}).

Похоже, что он выполняется до того, как DOM готов.