переместить выбранный элемент с помощью клавиш со стрелками в javascript - PullRequest
0 голосов
/ 12 июля 2020

У меня есть список элементов, я хочу иметь возможность выбрать элемент (щелчком мыши) и перемещать только этот конкретный элемент с помощью клавиш со стрелками. Я сделал движущуюся часть, но когда я выбираю второй элемент, он также перемещает ранее выбранный элемент. Или, если я дважды щелкну тот же элемент, он вернет его в исходное положение.

Я предполагаю, что это из-за того, что положение относительное? Хотя я пытался изменить его на абсолютный и родительский div как относительный, все равно не сработало. Я также пробовал использовать поля, но возникла та же проблема.

move();

function move(){
    let list_items = document.querySelectorAll('.list-item');


    for (let i = 0; i < list_items.length; i ++){
        let list=list_items[i];

        list.addEventListener('click',function(){

            console.log(list);
            var objImage= null;
            objImage=list;              
            objImage.style.position='relative';
            objImage.style.left='0px';
            objImage.style.top='0px';

            
            function getKeyAndMove(e){  
                            
                var key_code=e.which||e.keyCode;
                switch(key_code){
                    case 37: //left arrow key
                    moveLeft();
                    break;
                    case 38: //Up arrow key
                    moveUp();
                    break;
                    case 39: //right arrow key
                    moveRight();
                    break;
                    case 40: //down arrow key
                    moveDown();
                    break;
                    default:
                    console.log(e);                         
                }
            }
            function moveLeft(){
                objImage.style.left=parseInt(objImage.style.left)-5 +'px';
                // objImage.style.position='static';
            }
            function moveUp(){
                objImage.style.top=parseInt(objImage.style.top)-5 +'px';
                // objImage.style.position='static';
            }
            function moveRight(){
                objImage.style.left=parseInt(objImage.style.left)+5 +'px';
                // objImage.style.position='static';
            }
            function moveDown(){
                objImage.style.top=parseInt(objImage.style.top)+5 +'px';
                // objImage.style.position='static';
            }
            window.addEventListener("keydown", getKeyAndMove);
        });
    }
}
.list {
    display: flex;
    flex-flow: column;
    flex: 1;

    width: 100%;
    min-width: 250px;
    max-width: 350px;
    height: 100%;
    min-height: 150px;

    background-color: rgba(0, 0, 0, 0.1);
    margin: 0 15px;
    padding: 8px;
    transition: all 0.2s linear;
}

.list .list-item {
    background-color: #F3F3F3;
    border-radius: 8px;
    padding: 15px 20px;
    text-align: center;
    margin: 4px 0px;
}
            <div class="list" id="list"> 
                <h2>Menu Items</h2>
 
                <div class="list-item" draggable="true">List item 1</div>
                <div class="list-item" draggable="true">List item 2</div>
                <div class="list-item" draggable="true">List item 3</div>
            </div>

EDIT заставил его работать с помощью решения, предложенного @rexfordkelly. Вот ссылка на игровую площадку, которой он поделился jsfiddle.net / r7ao2n5f / 1

1 Ответ

0 голосов
/ 12 июля 2020

Если я понимаю ваш вопрос и ваше желаемое поведение:

Перемещение одного или нескольких выбранных элементов, выбор выполняется с помощью мыши, а перемещение выполняется нажатием клавиш, вверх, вниз, влево и вправо.

Я думаю, что у вас это в значительной степени есть, единственное, что ваш выбор никогда не очищается, что должно происходить, когда любой щелчок происходит после того, как был сделан ход.

Вы можете рассмотреть возможность моделирования поведения в режимы.

  • выбор
  • перемещение

Где поведение, выполненное в псевдокоде, будет примерно таким:

let mode = 0; // selection mode
let selections = [];

... key press event Listeners
... click event Listeners

function processAction( action, event ) {
    If ( 'click' == action && 0 != mode ){ // was in move mode
        mode = 0; // Set to selection mode.
        selections = []; // resets the selections made
        ... // reset DOM, and clear any currently decorated elements
    }

    if ( 'click' == action) {
        selections.push(event.targetElement);
        ...// Update DOM and decorate elements
    }

    If ( 'move' === action && mode !== 1) {
        mode = 1; // This enters us into "Move" mode.
    }

    If ( 'move' === action ){
        // Execute moving logic
    }
}

Чтобы решить проблему с двойным щелчком.

Или, если я дважды щелкну тот же элемент, он вернется в исходное положение

Это результат определенного «стандартного» поведения или «предустановок» вашего браузера в отношении того, как он ведет себя, когда пользователь перетаскивает элемент. Вы можете отключить это «стандартное» поведение двумя способами, один из них - с небольшим CSS

.list-item  { 
  -webkit-user-drag: none; 
  -khtml-user-drag: none; 
  -moz-user-drag: none; 
  -o-user-drag: none; 
  user-drag: none; 
}
 

. Подробнее об этом «стандартном» поведении на MDN можно узнать здесь , которое гласит :

Если этот атрибут не установлен, его значение по умолчанию - auto, что означает, что поведение перетаскивания является поведением браузера по умолчанию: можно перетаскивать только выделенный текст, изображения и ссылки ...

О, и я забыл упомянуть, вы можете просто прикрепить слушателей событий к элементу id="list", так как события щелчка всех дочерних элементов будут всплывать и перехватываться.

Вы можете найти подробную информацию о том, как чтобы выяснить, какой элемент был нажат здесь и больше о том, как всплывают события здесь и на MDN здесь , в частности, в разделе «Объяснение всплывания и захвата»

PS: Я также видел в некоторых приложениях, где у них аналогичное поведение, выбор выполняется с помощью мыши и перемещается с помощью клавиш со стрелками. Они позволяют пользователю перемещаться на другое расстояние, когда клавиша «Shift» удерживается нажатой при нажатии клавиши со стрелкой.

...