0

ドラッグ可能な HTML5 リストの実装に取り​​組んでおり、問題が発生しています。

基本的に、要素をドラッグするときはいつでも、今入力した要素の直前または直後に、ドラッグしている要素を挿入します。これは、マウスを動かすと、要素がマウスの下の位置に移動し続けることを意味します。(visibility: hidden要素に設定したため、空白として表示されます。) 要素をドロップすると、要素の位置を記述した AJAX 呼び出しがサーバーに送信され、サーバー上で移動が実行されます。

問題は、何らかの理由でドロップ イベントが発生せず (ハンドラーのブレークポイントがヒットしない)、ドラッグ イメージが開始した場所にスナップバックすることです。(もちろん、要素ページ上で移動したため、新しい場所に再表示されますが、drop が発生しないため、サーバーには変更が通知されません。) 何が起こっているか知っている人はいますか? 通常の答えは「dragenter/dragover を呼び出す必要があります」ですがpreventDefault()、私はすでにそれを行っています。

jQuery 1.10.2 を使用していますが、Safari 7.0.1 と Firefox 26.0 の両方でこの動作が見られます。ちなみに、Rails 4.0.2 はこのプロジェクトのフレームワークであり、jquery_ujs とターボリンクを使用しています。

関連コード:

var draggingLI;

$('ol[data-passage-id]').find('li > a').attr('draggable', 'true')
.on('dragstart', function (ev) {
    draggingLI = $(ev.target).closest("li")[0];

    ev.originalEvent.dataTransfer.effectAllowed = 'move';
    ev.originalEvent.dataTransfer.setData('text/plain', ev.target.href);
    ev.originalEvent.dataTransfer.setData('text/uri-list', ev.target.href);
})
.on('dragenter', function (ev) {
    ev.originalEvent.dataTransfer.dropEffect = 'move'; 
    $(draggingLI).css('visibility', 'hidden');

    if(canDropIn(ev.target)) {
        var droppingLI = $(ev.target).closest("li")[0];

        if(draggingLI == droppingLI) {
            // do nothing
        }
        if(draggingLI.nextElementSibling == droppingLI) {
            // We want to move the dragging element below this element.
            $(droppingLI).after(draggingLI);
        }
        else {
            // We want to move the dragging element above this element.
            $(droppingLI).before(draggingLI);
        }

        ev.preventDefault();
        ev.stopPropagation();
        return false;
    }
})
.on('dragover', function (ev) {
    if(canDropIn(ev.target)) {
        ev.preventDefault();
        ev.stopPropagation();
        return false;
    }
})
.on('drop', function (ev) {
    sendMovedItem(draggingLI);
    ev.preventDefault();
    ev.stopPropagation();
    return false;
})
.on('dragend', function (ev) {
    $(draggingLI).css('visibility', '');
});

canDropIn()は現在、常に を返すスタブですtruesendMovedItem()AJAX 呼び出しを行う関数です。コンソールにエラーはありません。

4

1 に答える 1

0

この問題は、ドラッグ要素自体を移動するという私の戦略が原因のようです。ドラッグ中に要素を移動するとブラウザに問題が発生するためなのか、元の要素へのドロップが許可されていないためなのかはわかりません。元の要素を完全に非表示にしてから、代わりに移動できるプレースホルダー要素を挿入することで、この問題を回避しました。(成功したドロップはすべてプレースホルダーで終了するため、dragenter/dragover/drop ハンドラーをプレースホルダーにアタッチする必要があります。)

ただし、誰かがアイデアを持っている場合は、プレースホルダーを必要としないソリューションを希望します!

于 2014-01-04T22:47:08.447 に答える