UL LI Positionen nach "droppable" wieder herstellen

Thomas_Jung

Erfahrenes Mitglied
Hallo zusammen,

ich möchte nicht die "photos li" verschieben sondern nur das Erbebnis erhalten.

Was muss ich tun, um das Verschieben zu verhindern!

Gruß Thomas Jung


Javascript:
$(document).ready(function(){
    $("#photos li").draggable({
       
    });    
    $(".gallery").droppable({    
        accept: '.ui-draggable',
        drop: function (event, ui) {    
            var gallery_id = $(this).attr('id').replace('gallery_', '');    
            var photo_id = ui.draggable.attr('id').replace('photo_', '');
            // $.post("saveToGallery.php", { gallery_id: gallery_id, photo_id: photo_id });
            alert('Das Foto mit der ID: ' + photo_id + ' wurde in die Gallerie:  ' + gallery_id + ' geladen' ); 
        }    
    });
});

<div id="gallery_1" class="gallery" style="padding:25px;">gallery 1</div>
<div id="gallery_2" class="gallery" style="padding:25px;">gallery 2</div>

<ul id="photos">
<li id="photo_1">photo 1</li>
<li id="photo_2">photo 2</li>
<li id="photo_3">photo 3</li>
</ul>
 

Sempervivum

Erfahrenes Mitglied
Mal sehen ob ich das richtig verstehe: Der Benutzer soll ein Foto auf eines der div.gallery ziehen. Wenn er die Maus los lässt, willst Du die Info haben auf welchem div das passiert ohne dass das Foto in das div.gallery verschoben wird?
 
Zuletzt bearbeitet:

Thomas_Jung

Erfahrenes Mitglied
Hallo Sempervivum,
richtig.
Ich möchte nur die Foto-ID und die jeweilige Galerie-ID haben, um die Foto-ID anschließend mit der Galerie-ID in einer Tabelle zu speichern.
Code:
// $.post("saveToGallery.php", { gallery_id: gallery_id, photo_id: photo_id });
Vielleicht denke ich auch zu kompliziert?
 

Sempervivum

Erfahrenes Mitglied
Ich weiß nicht, ob dir das entgegen kommt, aber ich habe an Hand der Beschreibung bei MDN:
Drag Operations - Web APIs | MDN
das Drag&Drop ohne jQuery implementiert:
Code:
    <div id="gallery_1" class="gallery" style="padding:25px;">gallery 1</div>
    <div id="gallery_2" class="gallery" style="padding:25px;">gallery 2</div>
    <div id="gallery_3" class="gallery" style="padding:25px;">gallery 3</div>

    <ul id="photos">
        <li id="photo_1" class="photo" draggable="true">photo 1</li>
        <li id="photo_2" class="photo" draggable="true">photo 2</li>
        <li id="photo_3" class="photo" draggable="true">photo 3</li>
    </ul>
    <script>
        // Symbol, das beim Ziehen angezeigt werden soll:
        const dragImg = new Image();
        dragImg.src = 'images/buttonplay.png';
        // Für alle Fotos beim Dragstart die ID des Bildes und das Symbol
        // in die Daten für das Ziehen eintragen:
        document.querySelectorAll('.photo').forEach(item => {
            item.addEventListener('dragstart', event => {
                event.dataTransfer.setData('text/plain', event.target.id);
                event.dataTransfer.setDragImage(dragImg, 0, 0);
            });
        });
        // Für alle Galerien:
        document.querySelectorAll('.gallery').forEach(item => {
            // Beim Dragover die Default-Aktion deaktivieren,
            // damit wird das Element für ein Drop frei gegeben:
            item.addEventListener('dragover', (event) => {
                event.preventDefault();
            });
            // Aktionen beim Drop: ID der Galerie und des Fotos bereit stellen:
            item.addEventListener('drop', event => {
                const
                    idGallery = event.target.id,
                    idPhoto = event.dataTransfer.getData('text/plain');
                console.log('ID des Fotos=' + idPhoto + ', ID der Gallerie=' + idGallery);
            });
        });
    </script>
Statt eines Bildes mit einem Icon kann man auch das Quellbild selber beim Ziehen anzeigen:
Code:
    <div id="gallery_1" class="gallery" style="padding:25px;">gallery 1</div>
    <div id="gallery_2" class="gallery" style="padding:25px;">gallery 2</div>
    <div id="gallery_3" class="gallery" style="padding:25px;">gallery 3</div>

    <ul id="photos">
        <li id="photo_1" class="photo" draggable="true">
            <img src='images/dia0.jpg'>
        </li>
        <li id="photo_1" class="photo" draggable="true">
            <img src='images/dia1.jpg'>
        </li>
        <li id="photo_1" class="photo" draggable="true">
            <img src='images/dia2.jpg'>
        </li>
    </ul>
    <script>
        document.querySelectorAll('.photo').forEach(item => {
            item.addEventListener('dragstart', event => {
                event.dataTransfer.setData('text/plain', event.target.id);
                const img = event.target;
                event.dataTransfer.setDragImage(img, 0, 0);
            });
        });
        document.querySelectorAll('.gallery').forEach(item => {
            item.addEventListener('dragover', (event) => {
                event.preventDefault();
            });
            item.addEventListener('drop', event => {
                const
                    idGallery = event.target.id,
                    idPhoto = event.dataTransfer.getData('text/plain');
                console.log('ID des Fotos=' + idPhoto + ', ID der Gallerie=' + idGallery);
            });
        });
    </script>
 
Zuletzt bearbeitet:

Sempervivum

Erfahrenes Mitglied
PS: Wie ich gerade sehe, zeigt der Browser das Bild automatisch beim Ziehen an, man braucht es also gar nicht in die Daten zu übertragen.
 

Thomas_Jung

Erfahrenes Mitglied
Hallo Sempervivum,
vielen Dank erstmal für deine Zeit.

Wenn ich bei deinen Beispielen ein Bild in die jeweilige Galerie ziehe versucht er jeweils die Seite im Browser aufzurufen.

GET http://photo_1/

Ist das so gewollt?
 

Sempervivum

Erfahrenes Mitglied
Nein, das ist natürlich nicht so gewollt und ist bei mir auch nicht passiert. Außer den Ausgaben in der Console ist beim Drop nichts passiert. Hast Du vielleicht noch irgend etwas an Javascript eingebunden, z. B. jQuery-UI?
Mit welchem Browser hast Du getestet?
Sieht dein HTML vielleicht anders aus, z. B. ein Link darin?
 

Thomas_Jung

Erfahrenes Mitglied
Im Firefox tritt das Problem auf.
Im Microsoft Edge passiert überhaupt nichts. (Keine Ausgabe in der Konsole)
Im Google Chrome passiert auch nichts. (Keine Ausgabe in der Konsole)
:confused:

jQuery-UI habe ich entfernt.
 

Sempervivum

Erfahrenes Mitglied
Das im Firefox konnte ich reproduzieren, wenn es sich um ein Bild handelt, öffnet er eine neue Seite mit dem Bild darin. Man kann das leicht unterbinden, indem man auch für dieses Event "drop" die Defaulaktion unterdrückt:
Code:
        document.querySelectorAll('.photo').forEach(item => {
            item.addEventListener('dragstart', event => {
                event.dataTransfer.setData('text/plain', event.target.id);
                const img = event.target;
                event.dataTransfer.setDragImage(img, 0, 0);
            });
        });
        document.querySelectorAll('.gallery').forEach(item => {
            item.addEventListener('dragover', (event) => {
                event.preventDefault();
            });
            item.addEventListener('drop', event => {
                // Default-Aktion unterdrücken:
                event.preventDefault();
                const
                    idGallery = event.target.id,
                    idPhoto = event.dataTransfer.getData('text/plain');
                console.log('ID des Fotos=' + idPhoto + ', ID der Gallerie=' + idGallery);
            });
        });
In Chrome und Edge funktioniert es bei mir, die Ausgabe in der Console kommt. Kannst Du es online stellen und die URL posten?