Avatar billede haunted Nybegynder
20. december 2010 - 20:41 Der er 2 kommentarer og
1 løsning

Drag & Drop upload via submit

Hej Eksperter.

Jeg har lavet en Drag & Drop side hvor jeg kan droppe filer i en div som så aktiverer en upload funktion, der via en java controller, uploader til et fileshare.

Nu vil jeg gerne have at det sker når jeg trykker på submit i stedet for når jeg hiver filerne hen på div'en. Hvordan gør jeg det??

Dvs. filerne skal på en eller anden måde gemmes på formen og kunne sendes med på når der submittes.

Jsp side:

<CODE>
<html>
    <head>
        <title>Drag and drop</title>
       
        <script type="text/javascript" src="scripts.js"></script>
       
        <link rel="stylesheet" href="styles.css" type="text/css"> 
    </head>
   
<body>
    <div id="status"></div>
    <div id="drop"></div>
    <div id="list"></div>
    <input type="button" onclick="uploadFiles();" value="Upload">
   
    <script>setupDragAndDropEvents();</script>
</body>
</html>
</CODE>

scripts.js

<CODE>
function setupDragAndDropEvents()
{
    new uploader('drop', 'status', 'upload.html', 'list');
}

function uploader(place, status, targetPHP, show) {
   
    // Upload image files
    upload = function(file) {
   
        // Firefox 3.6, Chrome 6, WebKit
        if(window.FileReader) {

            // Once the process of reading file
            this.loadEnd = function() {
            }
               
            // Loading errors
            this.loadError = function(event) {
                switch(event.target.error.code) {
                    case event.target.error.NOT_FOUND_ERR:
                        document.getElementById(status).innerHTML = 'File not found!';
                    break;
                    case event.target.error.NOT_READABLE_ERR:
                        document.getElementById(status).innerHTML = 'File not readable!';
                    break;
                    case event.target.error.ABORT_ERR:
                    break;
                    default:
                        document.getElementById(status).innerHTML = 'Read error.';
                }   
            }
       
            // Reading Progress
            this.loadProgress = function(event) {
                if (event.lengthComputable) {
                    var percentage = Math.round((event.loaded * 100) / event.total);
                    document.getElementById(status).innerHTML = 'Loaded : ' + percentage + '%';
                }               
            }
        reader = new FileReader();
       
        // Firefox 3.6, WebKit
        if(reader.addEventListener) {
            reader.addEventListener('loadend', this.loadEnd, false);
            if (status != null)
            {
                reader.addEventListener('error', this.loadError, false);
                reader.addEventListener('progress', this.loadProgress, false);
            }
       
        // Chrome 7
        } else {
            reader.onloadend = this.loadEnd;
            if (status != null)
            {
                reader.onerror = this.loadError;
                reader.onprogress = this.loadProgress;
            }
        }

        var preview = new FileReader();
       
        // Firefox 3.6, WebKit
        if(preview.addEventListener) {
            //preview.addEventListener('loadend', this.previewNow, false);
        // Chrome 7   
        } else {
            //preview.onloadend = this.previewNow;
        }
       
        // The function that starts reading the file as a binary string
        reader.readAsBinaryString(file);
       
        // Preview uploaded files
        if (show) {
            //preview.readAsDataURL(file);
        }
       
          // Safari 5 does not support FileReader
        } else {
            xhr = new XMLHttpRequest();
            xhr.open('POST', targetPHP+'?up=true', true);
            xhr.setRequestHeader('UP-FILENAME', file.name);
            xhr.setRequestHeader('UP-SIZE', file.size);
            xhr.setRequestHeader('UP-TYPE', file.type);
            xhr.send(file);
           
            if (status) {
                document.getElementById(status).innerHTML = 'Loaded : 100%';
            }
           
            if (show) {
                var newFile  = document.createElement('div');
                newFile.innerHTML = 'Loaded : ' + file.name + ' size ' + file.size+' B';
                document.getElementById(show).appendChild(newFile);
            }   
        }               
    }

    // Function drop file
    this.drop = function(event) {
        event.preventDefault();

        var data = event.dataTransfer;

        var boundary = '------multipartformboundary' + (new Date).getTime();
        var dashdash = '--';
        var crlf    = '\r\n';

        // Build RFC2388 string
        var builder = '';

        builder += dashdash;
        builder += boundary;
        builder += crlf;
       
        var xhr = new XMLHttpRequest();
       
        // For each dropped file
        for (var i = 0; i < data.files.length; i++) {
            var file = data.files[i];

            // Generate headers           
            builder += 'Content-Disposition: form-data; name="filedata[]"';
            if (file.fileName) {
              builder += '; filename="' + file.fileName + '"';
            }
            builder += crlf;

            builder += 'Content-Type: ' + file.type;
            //builder += 'Content-Type: application/octet-stream';
            builder += crlf;
            builder += crlf;

            // Append binary data
            builder += file.getAsBinary();
            builder += crlf;

            // Write boundary
            builder += dashdash;
            builder += boundary;
            builder += crlf;
        }
       
        // Mark end of the request
        builder += dashdash;
        builder += boundary;
        builder += dashdash;
        builder += crlf;

        xhr.open("POST", "upload.html?up=true", true);
        xhr.setRequestHeader('content-type', 'multipart/form-data; boundary=' + boundary);
        xhr.sendAsBinary(builder);       

        // Prevent FireFox opening the dragged file
        event.stopPropagation();
    }
   
    // The inclusion of the event listeners (DragOver and drop)

    this.uploadPlace = document.getElementById(place);
    this.uploadPlace.addEventListener("dragover",
        function(event) {
            event.stopPropagation();
            event.preventDefault();
        }, true);
    this.uploadPlace.addEventListener("drop", this.drop, false);
}
</CODE>

På forhånd tak for hjælpen :)
Avatar billede heinzdmx Nybegynder
20. december 2010 - 22:00 #1
Dette er ikke en løsning på dit problem, men blot et forslag til en anden måde at løse det på. Kig på plUpload, det er crossbrowser, og fungere med Flash, Gears, HTML 5, Silverlight, BrowserPlus og HTML 4.

Drag'n'drop virker med Gears, og browserplus og i firefox med HTML 5. Derudover kan du lave clientside billed formindskelse.

Plupload.com
Avatar billede haunted Nybegynder
21. december 2010 - 21:51 #2
tak for svaret. Men jeg tror det er lidt for overkill til det jeg skal bruge det til og så vil jeg egentlig gerne selv have koden liggende uden nogen 3. parts scripts. Jeg kunne dog prøve at afkode de scripts der ligger men det vil tage noget tid.

Nogen der har andre forslag?
Avatar billede haunted Nybegynder
30. december 2010 - 12:50 #3
Ok nu har jeg løsningen på denne:

Jeg har gemt filerne på uploader objektet i et array se nedenstående forklaring.

Jeg initierer med en instans jeg kan få fat i igen

[CODE]
function setupDragAndDropEvents()
{
    uploader uploaderInst = new uploader('drop', 'status', 'upload.html', 'list');
}
[/CODE]

Jeg laver mit array som jeg gemmer filerne i.

[CODE]
function uploader(place, status, targetPHP, show) {

    var m = [];
   
    // Upload image files
    upload = function(file...
...
...
[/CODE]

this.drop = function(event) {

ændres til

this.upload = function(event) {

i en ny drop function laver jeg så overførslen til arrayet:

[CODE]
    this.drop = function(event) {
...
...
    for (idx = 0; idx < event.dataTransfer.files.length; idx++) {
        file = event.dataTransfer.files[idx];
        m.push(file);
    }
...
...
[/CODE]

Nu skal jeg så kalde instansen, som jeg lavede tidligere, på min button.

<input type="button" onclick="uploaderInst.upload();" value="Upload">

Nu skulle den gerne sende requestet til serveren når der trykkes på Upload knappen.

Dog skal upload funktionen så hive fat i m[] og ikke event.dataTransfer.files[] objektet.

----

Hvis det er forvirrende kan jeg godt lave et komplet eksempel men kun hvis der er nogen der efterspørger det.
Avatar billede Ny bruger Nybegynder

Din løsning...

Tilladte BB-code-tags: [b]fed[/b] [i]kursiv[/i] [u]understreget[/u] Web- og emailadresser omdannes automatisk til links. Der sættes "nofollow" på alle links.

Loading billede Opret Preview
Kategori
Vi tilbyder markedets bedste kurser inden for webudvikling

Log ind eller opret profil

Hov!

For at kunne deltage på Computerworld Eksperten skal du være logget ind.

Det er heldigvis nemt at oprette en bruger: Det tager to minutter og du kan vælge at bruge enten e-mail, Facebook eller Google som login.

Du kan også logge ind via nedenstående tjenester