Here은 외부 라이브러리가 필요없고 JQueryUI Sortables를 사용하지 않고 JS와 JQuery를 사용하여 작성한 솔루션입니다.
HTML : list_container
개별 list_item
요소를 보유하고
<div class="list_container">
<div class="list_item">One</div>
<div class="list_item">Two</div>
<div class="list_item">Three</div>
<div class="list_item">Four</div>
<div class="list_item">Five</div>
<div class="list_item">Six</div>
</div>
. 두 사람의 후자가 정렬 된 목록을 만들기 위해 이동할 수 있습니다. list_item
안에 원하는 것을 넣을 수 있으며 여전히 잘 작동합니다.
CSS :
.list_container {
position: relative;
}
.list_item {
position: absolute;
z-index: 0;
left: 0px;
}
.list_item.selected {
z-index: 1000;
}
은 CSS 규칙의 전체 목록 (만 필요한 사람은 위의 도시)에 대한 this 바이올린을 방문하시기 바랍니다.
자바 스크립트 :
나는이 비트 단위를 통과 한 후 하단에 전체 코드를 보여 드리겠습니다.
첫째로, 나는이 (페이지로드시) 동적으로 클래스를 만드는 데 사용되는 자신의 기록 대응
var classes = new Array("one", "two", "three", ...);
과 인덱스 번호를 일치하는 배열을 정의했다. 이러한 클래스는 목록을 정렬하는 데 사용됩니다. 목록에있는 수만큼 항목을 채우기 만하면됩니다. 이것은 제가 작성한 코드의 하나의 몰락이며,이 문제를 극복하는 방법을 확신하지 못합니다 (수백 가지 항목 이상을 나열하기 위해 요소를 입력하는 것이 매우 지루합니다!)
다음으로 다른 변수 :
var margin = 2; // Space desired between each list item
var $el; // Used to hold the ID of the element that has been selected
var oldPos = 0; // The position of the selected element BEFORE animation
var newPos = 0; // The position of the selected element AFTER animation (also current position)
var dragging = false; // Whether or not an item is being moved
var numElements = $('.list_container > div').length;
// selectionHeight is the height of each list element (assuming all the same height)
// It includes the div height, the height of top and bottom borders, and the desired margin
var selectionHeight = $('.list_container .list_item').height() + parseInt($('.list_container .list_item').css("border-bottom-width")) + parseInt($('.list_container .list_item').css("border-top-width")) + margin;
var classInfo = ''; // classInfo will be populated with the information that is used to dynamically create classes upon page load
페이지를로드 할 때, 각 list_item
통과하고 목록에서 초기 위치에 따라 그것을 클래스를 지정합니다. 또한 classInfo
에 목록 항목의 TOP 위치를 추가하십시오.
$('.list_container .list_item').each(function (index) {
$(this).addClass(classes[index]);
classInfo += '.' + classes[index] + ' {top: ' + index * selectionHeight + 'px;}\n';
});
이제 위에서 작성한 classInfo
을 사용하여 페이지에 클래스를 동적으로 작성하십시오.
var style = document.createElement('style');
style.type = 'text/css';
style.innerHTML = classInfo;
document.getElementsByTagName('head')[0].appendChild(style);
위의 코드 비트는 필요한 클래스를 페이지의 HTML에 기록합니다. 페이지의 소스를 보면 페이지의 머리 부분에 클래스가 표시됩니다.
이제 주문 부탁드립니다.다음과 같이 첫째, mousedown
$('.list_item').mousedown(function (ev) {
$el = $(this);
oldPos = $el.index() + 1;
newPos = oldPos;
dragging = true;
startY = ev.clientY; // Gets the current mouse position
startT = parseInt($el.css('top')); // Gets the current position of the TOP of the item
$el.addClass('selected'); // Adding class brings it to top (z-index) and changes color of list item
});
다음으로, mousemove
및 mouseup
기능을 함께 마지막
$(window).mousemove(function (ev) { // Use $(window) so mouse can leave parent div and still work
if (dragging) {
$el.attr('class', 'list_item') // Remove the numbered class (.one, .two, etc)
$el.addClass('selected'); // Add this class back for aesthetics
// ----- calculate new top
var newTop = startT + (ev.clientY - startY);
$el.css('cursor', 'pointer');
// ------
//------ stay in parent
var maxTop = $el.parent().height() - $el.height();
newTop = newTop < 0 ? 0 : newTop > maxTop ? maxTop : newTop;
$el.css('top', newTop);
//------
newPos = getPos(newTop, selectionHeight); // Determine what the current position of the selected list item is
// If the position of the list item has changed, move the position's current element out of the way and reassign oldPos to newPos
if (oldPos != newPos) {
moveThings(oldPos, newPos, selectionHeight);
oldPos = newPos;
}
}
}).mouseup(function() {
dragging = false; // User is no longer dragging
$el.removeClass('selected'); // Element is no longer selected
setNewClass($el, newPos); // Set the new class of the moved list item
$el.css('top', (newPos - 1) * selectionHeight); // Position the moved element where it belongs. Otherwise it'll come to rest where you release it, not in its correct position.
});
연결되어, 세 가지 기능 getPos
, moveThings
및 setNewClass
은 다음과 같습니다
function getPos(a, b) { // a == newTop, b == selectionHeight
return Math.round((a/b) + 1);
}
getPos
작품 선택된 엘멘 (elemen) t가 현재 입력되어 있습니다. newTop이 0.5b보다 작 으면 영역 1에 있습니다. 0.5b와 1.5b 사이에 있으면 영역 2입니다. 1.5b와 2.5b 사이에 있으면 영역 3에 있습니다. . 종이에 몇 가지 사례를 작성하면 무슨 일이 일어나는지 이해할 수 있습니다.
위의 함수는 실제 애니메이션 부분을 무엇입니까 및 선택한 목록 항목을 수용하기 위해 주위에 목록 항목을 이동합니다. 모든 자바 스크립트 함께
function setNewClass(e, a) { // e == selected element, a == newPos
// Remove 'selected' class, then add back the 'list_item' class and the new numbered class
e.attr('class', 'list_item').addClass(classes[a-1]);
}
** : **
var classes = new Array("one", "two", "three", "four", "five", "six", "seven", "eight", "nine", "ten", "eleven", "twelve", "thirteen", "fourteen", "fifteen", "sixteen", "seventeem", "eighteen", "nineteen", "twenty", "twentyone", "twentytwo", "twentythree", "twentyfour");
$(document).ready(function() {
var margin = 2;
var $el;
var oldPos = 0;
var newPos = 0;
var dragging = false;
var selectionHeight = $('.list_container .list_item').height() + parseInt($('.list_container .list_item').css("border-bottom-width")) + parseInt($('.list_container .list_item').css("border-top-width")) + margin;
var classInfo = '';
$('.list_container .list_item').each(function (index) {
$(this).addClass(classes[index]);
classInfo += '.' + classes[index] + ' {top: ' + index * selectionHeight + 'px;}\n';
});
var style = document.createElement('style');
style.type = 'text/css';
style.innerHTML = classInfo;
document.getElementsByTagName('head')[0].appendChild(style);
$('.list_item').mousedown(function (ev) {
$el = $(this);
oldPos = $el.index() + 1;
newPos = oldPos;
dragging = true;
startY = ev.clientY;
startT = parseInt($el.css('top'));
$el.addClass('selected');
});
$(window).mousemove(function (ev) {
if (dragging) {
$el.attr('class', 'list_item')
$el.addClass('selected');
// ----- calculate new top
var newTop = startT + (ev.clientY - startY);
$el.css('cursor', 'pointer');
// ------
//------ stay in parent
var maxTop = $el.parent().height() - $el.height();
newTop = newTop < 0 ? 0 : newTop > maxTop ? maxTop : newTop;
$el.css('top', newTop);
//------
newPos = getPos(newTop, selectionHeight);
if (oldPos != newPos) {
moveThings(oldPos, newPos, selectionHeight);
oldPos = newPos;
}
}
}).mouseup(function() {
dragging = false;
$el.removeClass('selected');
setNewClass($el, newPos);
$el.css('top', (newPos - 1) * selectionHeight);
});
});
function getPos(a, b) { // a == topPos, b == selectionHeight
return Math.round((a/b) + 1);
}
function moveThings(a, b, c) { // a == oldPos, b == newPos, c == selectedHeight
var first = classes[b - 1];
var $newEl = $('.list_container .' + first);
if (a < b) { // oldPos less than newPos
var second = classes[b - 2];
var newTop = parseInt($newEl.css('top')) - c;
} else { // oldPos more than newPos
var second = classes[b];
var newTop = parseInt($newEl.css('top')) + c;
}
$newEl.css('top', parseInt($newEl.css('top')));
$newEl.removeClass(first);
$newEl.animate({
top: newTop
}, 300, function() {
$newEl.removeAttr('style');
});
$newEl.addClass(second);
return false; // Cleans up animations
}
function setNewClass(e, a) { // e == selected element, a == newPos
e.attr('class', 'list_item').addClass(classes[a - 1]);
}
jQueryUI의 sortables 당신을 위해 이런 종류의 작업을 수행 ... – dandavis
는 그래서 않습니다. 전에는 들어 보지 못했습니다. [this] (https://jqueryui.com/sortable/) 링크를 보면, 엘리먼트에 수평 자유도가 없도록 작성할 수 있는지 여부를 머리 부분에서 빨리 알 수 있습니까? 제 예제처럼 수직으로 만 움직이는 것을 선호합니다. – Birrel
yes : http://api.jqueryui.com/sortable/#option-axis – dandavis