javascript - Image preview script breaks on uploading the same image that was previously deleted - Stack Overflow

I am using this package, and I have modified it a bit, so that I can upload, drag and sort the images a

I am using this package, and I have modified it a bit, so that I can upload, drag and sort the images and preview them in the browser. Uploading works fine, and deleting of images. But I found a scenario when the script breaks. When I have more than one image and I delete the first image, on trying to upload the same image that I deleted the script doesn't work anymore. But if I don't try to upload the same image immediately and first upload some other and then the one that was deleted, then it works. Also, I don't get any errors in the console. I am not sure how to fix this.

My full code is here.

This is part of the code:

$(document).ready(function () {

    var imageCounter = 0;

    $('#articleForm').submit(function () {
        uploadPosition();
    });

    function uploadPosition() {
        var uploadedImagesPositions = [];
        $.each($('.jFiler-item-thumb-image'), function (index, value) {
            $(this).attr('data-position-index', index);
            uploadedImagesPositions[index] = $(this).find('img').attr('src');
        });

        if (!$('input[name="uploadedItems"]').length) {
            $('<input>', {
                type: "hidden",
                name: "uploadedItems"
            }).appendTo('#articleForm')
        }
        $('input[name="uploadedItems"]').val(JSON.stringify(uploadedImagesPositions));
        $("input[name^='jfiler-items-exclude-']:hidden").detach();
        console.log(uploadedImagesPositions);
    }

    $('#upload').filer({
        limit: null,
        maxSize: null,
        extensions: null,
        changeInput: '<div class="jFiler-input-dragDrop"><h1>+</h1></div>',
        showThumbs: true,
        appendTo: '.uploaded_items',
        theme: "default",
        templates: {
            box: '<div class="jFiler-item-list"></div>',
            item: '<div class="jFiler-item img-container dragdiv"></div>',
            itemAppend: '<div class="jFiler-item img-container dragdiv"></div>',
            progressBar: '<div class="bar"></div>',
            itemAppendToEnd: false,
            removeConfirmation: false,
            _selectors: {
                list: '.jFiler-item-list',
                item: '.jFiler-item',
                progressBar: '.bar',
                remove: '.jFiler-item-trash-action',
            }
        },
        uploadFile: {
            url: "/admin/articles/ajax",
            data: {
                '_token': $('input[name="_token"]').val()
            },
            type: 'POST',
            enctype: 'multipart/form-data',
            beforeSend: function () {},
            success: function (data, el) {
                uploadedImagesPositions = [];
                console.log(data);
                var filenameArray = data.split('/');
                var name = filenameArray.slice(-1).pop();
                var filename = name.replace(/[\/\s()]/g, '');

                var imageContainer = $('[data-jfiler-index="' + imageCounter + '"]').first();

                $('<div class="jFiler-item-thumb-image"><img src="/imagecache/thumb/' + filename + '"></div><div class="overlay"><a href="#"><span><i class="jFiler-item-trash-action ion-trash-a"></span></a></div>').appendTo(imageContainer);
                imageCounter++;

                $(".dragdiv").each(function () {
                    makeElementAsDragAndDrop($(this));
                });

                $('.images-refresh').hide();
                $('.images-refresh').click(function () {
                    $(this).closest("form").submit()
                });

                function makeElementAsDragAndDrop(elem) {
                    $(elem).draggable({
                        revert: "invalid",
                        cursor: "move",
                        helper: "clone"
                    });
                    $(elem).droppable({
                        activeClass: "ui-state-hover",
                        hoverClass: "ui-state-active",
                        drop: function (event, ui) {
                            uploadedImagesPositions = [];
                            $('.images-form a').hide();
                            $('.images-refresh').show();
                            var $dragElem = $(ui.draggable).clone().replaceAll(this);
                            $(this).replaceAll(ui.draggable);
                            makeElementAsDragAndDrop(this);
                            makeElementAsDragAndDrop($dragElem);
                        }
                    });
                }

                var parent = el.find(".jFiler-jProgressBar").parent();
                el.find(".jFiler-jProgressBar").fadeOut("slow", function () {
                    $("<div class=\"jFiler-item-others text-success\"><i class=\"icon-jfi-check-circle\"></i> Success</div>").hide().appendTo(parent).fadeIn("slow");
                });
            },
            error: function (el) {
                console.log(el);
                var parent = el.find(".jFiler-jProgressBar").parent();
                el.find(".jFiler-jProgressBar").fadeOut("slow", function () {
                    $("<div class=\"jFiler-item-others text-error\"><i class=\"icon-jfi-minus-circle\"></i> Error</div>").hide().appendTo(parent).fadeIn("slow");
                });
            },
            statusCode: {},
            onProgress: function () {},
        },
        dragDrop: {
            dragEnter: function () {},
            dragLeave: function () {},
            drop: function () {},
        },
        addMore: true,
        clipBoardPaste: true,
        excludeName: null,
        beforeShow: function () {
            return true
        },
        onSelect: function () {},
        afterShow: function () {},
        onRemove: function (el) {
            imageCounter = $('.img-container').size() - 1;
            //uploadPosition();
            //console.log(el.find('img').attr('src'));
        },
        onEmpty: function () {
            imageCounter = 0;
        },
        captions: {
            button: "Choose Files",
            feedback: "Choose files To Upload",
            feedback2: "files were chosen",
            drop: "Drop file here to Upload",
            removeConfirmation: "Are you sure you want to remove this file?",
            errors: {
                filesLimit: "Only {{fi-limit}} files are allowed to be uploaded.",
                filesType: "Only Images are allowed to be uploaded.",
                filesSize: "{{fi-name}} is too large! Please upload file up to {{fi-maxSize}} MB.",
                filesSizeAll: "Files you've choosed are too large! Please upload files up to {{fi-maxSize}} MB."
            }
        }
    });
});

Update

I have updated fiddle with HTML and CSS as well as javascript code, unfortunately, I couldn't get it to work, so not sure how helpful it is, but at least you can see the full code. I am using this scripts on my page where I upload images:

<script src=".2.3/jquery.min.js" integrity="sha384-I6F5OKECLVtK/BL+8iSLDEHowSAfUo76ZL9+kGAgTRdiByINKJaqTPH/QVNS1VDb" crossorigin="anonymous"></script>
<script type="text/javascript" src="{{ asset('js/foundation/foundation.min.js') }}"></script>
<script>$(document).foundation();</script>
<script type="text/javascript" src="{{ asset('js/jquery-ui/jquery-ui.min.js') }}"></script>
<script type="text/javascript" src="{{ asset('js/jquery-filer/jquery-filer.js') }}"></script>

jquery-filer is the script that I use for upload, the one that I have in fiddle.

And this is my server-side function for ajax upload. I am using PHP laravel in the backend:

public function ajaxUpload() {

    if (Input::hasFile('file')) {
        $files = Input::file('file');

        foreach ($files as $file) {
            $time = microtime(true);
            $name = $file->getClientOriginalName();
            $filename = $time.'-'.preg_replace('/[(\)\s]/u', '', $name);

            if(substr($file->getMimeType(), 0, 5) == 'image') {

                try {
                    $original = Image::make($file)->save(public_path($this->destinationPath.'/'.$filename));
                    \Log::info('try: '.$filename."\n");

                } catch (Exception $e) {
                    \Log::info('Caught exception: '.$e->getMessage(). "\n");
                }

                $img = Image::cache(function($image) use ($original){
                    return $image->make($original);
                });
            }
        }
    }

    return $this->destinationPath.$filename;
}

I am using this package, and I have modified it a bit, so that I can upload, drag and sort the images and preview them in the browser. Uploading works fine, and deleting of images. But I found a scenario when the script breaks. When I have more than one image and I delete the first image, on trying to upload the same image that I deleted the script doesn't work anymore. But if I don't try to upload the same image immediately and first upload some other and then the one that was deleted, then it works. Also, I don't get any errors in the console. I am not sure how to fix this.

My full code is here.

This is part of the code:

$(document).ready(function () {

    var imageCounter = 0;

    $('#articleForm').submit(function () {
        uploadPosition();
    });

    function uploadPosition() {
        var uploadedImagesPositions = [];
        $.each($('.jFiler-item-thumb-image'), function (index, value) {
            $(this).attr('data-position-index', index);
            uploadedImagesPositions[index] = $(this).find('img').attr('src');
        });

        if (!$('input[name="uploadedItems"]').length) {
            $('<input>', {
                type: "hidden",
                name: "uploadedItems"
            }).appendTo('#articleForm')
        }
        $('input[name="uploadedItems"]').val(JSON.stringify(uploadedImagesPositions));
        $("input[name^='jfiler-items-exclude-']:hidden").detach();
        console.log(uploadedImagesPositions);
    }

    $('#upload').filer({
        limit: null,
        maxSize: null,
        extensions: null,
        changeInput: '<div class="jFiler-input-dragDrop"><h1>+</h1></div>',
        showThumbs: true,
        appendTo: '.uploaded_items',
        theme: "default",
        templates: {
            box: '<div class="jFiler-item-list"></div>',
            item: '<div class="jFiler-item img-container dragdiv"></div>',
            itemAppend: '<div class="jFiler-item img-container dragdiv"></div>',
            progressBar: '<div class="bar"></div>',
            itemAppendToEnd: false,
            removeConfirmation: false,
            _selectors: {
                list: '.jFiler-item-list',
                item: '.jFiler-item',
                progressBar: '.bar',
                remove: '.jFiler-item-trash-action',
            }
        },
        uploadFile: {
            url: "/admin/articles/ajax",
            data: {
                '_token': $('input[name="_token"]').val()
            },
            type: 'POST',
            enctype: 'multipart/form-data',
            beforeSend: function () {},
            success: function (data, el) {
                uploadedImagesPositions = [];
                console.log(data);
                var filenameArray = data.split('/');
                var name = filenameArray.slice(-1).pop();
                var filename = name.replace(/[\/\s()]/g, '');

                var imageContainer = $('[data-jfiler-index="' + imageCounter + '"]').first();

                $('<div class="jFiler-item-thumb-image"><img src="/imagecache/thumb/' + filename + '"></div><div class="overlay"><a href="#"><span><i class="jFiler-item-trash-action ion-trash-a"></span></a></div>').appendTo(imageContainer);
                imageCounter++;

                $(".dragdiv").each(function () {
                    makeElementAsDragAndDrop($(this));
                });

                $('.images-refresh').hide();
                $('.images-refresh').click(function () {
                    $(this).closest("form").submit()
                });

                function makeElementAsDragAndDrop(elem) {
                    $(elem).draggable({
                        revert: "invalid",
                        cursor: "move",
                        helper: "clone"
                    });
                    $(elem).droppable({
                        activeClass: "ui-state-hover",
                        hoverClass: "ui-state-active",
                        drop: function (event, ui) {
                            uploadedImagesPositions = [];
                            $('.images-form a').hide();
                            $('.images-refresh').show();
                            var $dragElem = $(ui.draggable).clone().replaceAll(this);
                            $(this).replaceAll(ui.draggable);
                            makeElementAsDragAndDrop(this);
                            makeElementAsDragAndDrop($dragElem);
                        }
                    });
                }

                var parent = el.find(".jFiler-jProgressBar").parent();
                el.find(".jFiler-jProgressBar").fadeOut("slow", function () {
                    $("<div class=\"jFiler-item-others text-success\"><i class=\"icon-jfi-check-circle\"></i> Success</div>").hide().appendTo(parent).fadeIn("slow");
                });
            },
            error: function (el) {
                console.log(el);
                var parent = el.find(".jFiler-jProgressBar").parent();
                el.find(".jFiler-jProgressBar").fadeOut("slow", function () {
                    $("<div class=\"jFiler-item-others text-error\"><i class=\"icon-jfi-minus-circle\"></i> Error</div>").hide().appendTo(parent).fadeIn("slow");
                });
            },
            statusCode: {},
            onProgress: function () {},
        },
        dragDrop: {
            dragEnter: function () {},
            dragLeave: function () {},
            drop: function () {},
        },
        addMore: true,
        clipBoardPaste: true,
        excludeName: null,
        beforeShow: function () {
            return true
        },
        onSelect: function () {},
        afterShow: function () {},
        onRemove: function (el) {
            imageCounter = $('.img-container').size() - 1;
            //uploadPosition();
            //console.log(el.find('img').attr('src'));
        },
        onEmpty: function () {
            imageCounter = 0;
        },
        captions: {
            button: "Choose Files",
            feedback: "Choose files To Upload",
            feedback2: "files were chosen",
            drop: "Drop file here to Upload",
            removeConfirmation: "Are you sure you want to remove this file?",
            errors: {
                filesLimit: "Only {{fi-limit}} files are allowed to be uploaded.",
                filesType: "Only Images are allowed to be uploaded.",
                filesSize: "{{fi-name}} is too large! Please upload file up to {{fi-maxSize}} MB.",
                filesSizeAll: "Files you've choosed are too large! Please upload files up to {{fi-maxSize}} MB."
            }
        }
    });
});

Update

I have updated fiddle with HTML and CSS as well as javascript code, unfortunately, I couldn't get it to work, so not sure how helpful it is, but at least you can see the full code. I am using this scripts on my page where I upload images:

<script src="https://cdnjs.cloudflare./ajax/libs/jquery/2.2.3/jquery.min.js" integrity="sha384-I6F5OKECLVtK/BL+8iSLDEHowSAfUo76ZL9+kGAgTRdiByINKJaqTPH/QVNS1VDb" crossorigin="anonymous"></script>
<script type="text/javascript" src="{{ asset('js/foundation/foundation.min.js') }}"></script>
<script>$(document).foundation();</script>
<script type="text/javascript" src="{{ asset('js/jquery-ui/jquery-ui.min.js') }}"></script>
<script type="text/javascript" src="{{ asset('js/jquery-filer/jquery-filer.js') }}"></script>

jquery-filer is the script that I use for upload, the one that I have in fiddle.

And this is my server-side function for ajax upload. I am using PHP laravel in the backend:

public function ajaxUpload() {

    if (Input::hasFile('file')) {
        $files = Input::file('file');

        foreach ($files as $file) {
            $time = microtime(true);
            $name = $file->getClientOriginalName();
            $filename = $time.'-'.preg_replace('/[(\)\s]/u', '', $name);

            if(substr($file->getMimeType(), 0, 5) == 'image') {

                try {
                    $original = Image::make($file)->save(public_path($this->destinationPath.'/'.$filename));
                    \Log::info('try: '.$filename."\n");

                } catch (Exception $e) {
                    \Log::info('Caught exception: '.$e->getMessage(). "\n");
                }

                $img = Image::cache(function($image) use ($original){
                    return $image->make($original);
                });
            }
        }
    }

    return $this->destinationPath.$filename;
}
Share edited Sep 15, 2020 at 17:29 Alex 1,5801 gold badge15 silver badges27 bronze badges asked Jun 9, 2016 at 13:04 LudwigLudwig 1,84115 gold badges71 silver badges142 bronze badges 9
  • Any errors from the server or in the console? – mplungjan Commented Jun 9, 2016 at 13:15
  • No, I don't get any errors. – Ludwig Commented Jun 9, 2016 at 13:17
  • Is it possible image is being cached on delete? – yardpenalty. Commented Nov 10, 2016 at 19:46
  • 2 Can you cut the problem down and make a fiddle that suffers the issue? A running fiddle is the shortest route to a solution for you and I guess you are keen to find an answer since you set a bounty. So do a bit more work for us and you will be helping yourself to an earlier answer. – Vanquished Wombat Commented Nov 12, 2016 at 9:36
  • 3 Please include the full working example, with html and preferably css, with minimal code to help detecting what part of your code might be wrong. Right now, it seems like the options you provide for filer is too bloated and it is hard to see the actual problem. – Gokhan Kurt Commented Nov 12, 2016 at 12:26
 |  Show 4 more ments

3 Answers 3

Reset to default 0

I have tried to salvage the problem part in your code and came up with this (Fiddle).

The problem part is probably in the success function. Instead of trying to get element by its index, use the 2nd argument passed to the success function.

success: function(data, el) {
  uploadedImagesPositions = [];
  var filenameArray = data.split('/');
  var name = filenameArray.slice(-1).pop();
  var filename = name.replace(/[\/\s()]/g, '');

  // Instead of this
  // var imageContainer = $('[data-jfiler-index="' + imageCounter + '"]').first();

  // Use this
  var imageContainer = el;

  $('<div class="jFiler-item-thumb-image"><img src="/imagecache/thumb/' + filename + '"></div><div class="overlay"><a href="#"><span><i class="jFiler-item-trash-action ion-trash-a"></span></a></div>').appendTo(imageContainer );
}

The problem could also be caused by your server side, which we have no access right now.

Try to update to https://innostudio.de/fileuploader/ (jQuery.filer was transfered to the Fileuploader)

I was also using a JS image uploader which has the same type of issue. When a user uploads an image and deletes it and uploads the same image again, it does not work. So I fixed it using:

$('input[type="file"]').val(null);

in the image deleted event.

发布者:admin,转转请注明出处:http://www.yc00.com/questions/1745099043a4611160.html

相关推荐

发表回复

评论列表(0条)

  • 暂无评论

联系我们

400-800-8888

在线咨询: QQ交谈

邮件:admin@example.com

工作时间:周一至周五,9:30-18:30,节假日休息

关注微信