【问题标题】:How to make a draggable elements for touch and mouse(drag) events如何为触摸和鼠标(拖动)事件制作可拖动元素
【发布时间】:2019-11-04 07:20:44
【问题描述】:

我有以下用于拖放应用程序的代码,它可以在桌面上按预期工作,但是当我想在移动设备上使用该应用程序时,拖动事件无法按预期工作。我知道触摸事件是必需的,但是我不确定如何设置它们并实现这些功能。

<style>
    .objects {
        display:inline-block;
        background-color: #FFF3CC;
        border: #DFBC6A 1px solid;
        width: 50px;
        height: 50px;
        margin: 10px;
        padding: 8px;
        font-size: 18px;
        text-align: center;
        box-shadow: 2px 2px 2px #999;
        cursor: move;
    }
    #drop_zone {
        background-color: #EEE;
        border: #999 1px solid;
        width: 280px;
        height: 200px;
        padding: 8px;
        font-size: 18px;
    }
    </style>
  <h2 id="app_status">App status...</h2>
  <h1>Drop Zone</h1>
  <div id="drop_zone" ondragenter="drag_enter(event)" ondrop="drag_drop(event)" ondragover="return false" ondragleave="drag_leave(event)" ></div>
  <div id="object1" class="objects" draggable="true" ondragstart="drag_start(event)" ondragend="drag_end(event)">object 1</div>
  <div id="object2" class="objects" draggable="true" ondragstart="drag_start(event)" ondragend="drag_end(event)">object 2</div>
  <div id="object3" class="objects" draggable="true" ondragstart="drag_start(event)" ondragend="drag_end(event)">object 3</div>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.0.3/jquery.min.js"></script>
<script>
    function _(id){
       return document.getElementById(id);
    }
    var droppedIn = false;
    function drag_start(event) {
        _('app_status').innerHTML = "Dragging the "+event.target.getAttribute('id');
        event.dataTransfer.dropEffect = "move";
        event.dataTransfer.setData("text", event.target.getAttribute('id') );
    }
    function drag_enter(event) {
        _('app_status').innerHTML = "You are dragging over the "+event.target.getAttribute('id');
    }
    function drag_leave(event) {
        _('app_status').innerHTML = "You left the "+event.target.getAttribute('id');
    }
    function drag_drop(event) {
        event.preventDefault(); /* Prevent undesirable default behavior while dropping */
        var elem_id = event.dataTransfer.getData("text");
        _('app_status').innerHTML = "Dropped "+elem_id+" into the "+event.target.getAttribute('id');
        droppedIn = true;
          // Create our XMLHttpRequest object
          var hr = new XMLHttpRequest();
          // Create some variables we need to send to our PHP file
          var url = "jqueryserver.php";
          var vars = "value= "+elem_id;

          hr.open("POST", url, true);

          // Set content type header information for sending url encoded variables in the request
          hr.setRequestHeader("Content-type", "application/x-www-form-urlencoded");
          // Access the onreadystatechange event for the XMLHttpRequest object
          hr.onreadystatechange = function() {
            if(hr.readyState == 4 && hr.status == 200) {
              var return_data = hr.responseText;
            document.getElementById("app_status").innerHTML = return_data;
            }
          }
          // Send the data to PHP now... and wait for response to update the status div
          hr.send(vars); // Actually execute the request
          document.getElementById("app_status").innerHTML = event.target.getAttribute('id')+"processing...";
        }

    function drag_end(event) {
        if(droppedIn == false){
            _('app_status').innerHTML = "You let the "+event.target.getAttribute('id')+" go.";
        }
        droppedIn = false;
    }

</script>

【问题讨论】:

  • HammerJs 可能是一个不错的起点。这是一个简单且轻量级的库,可在您的网络应用中添加拖动和触摸事件支持。
  • 我希望避免使用库,并获得类似于stackoverflow.com/questions/1517924/…中提出的解决方案

标签: javascript drag-and-drop touch-event


【解决方案1】:

这个问题很老,但我把我的例子放在那里,用触摸和鼠标拖动元素,没有任何库

 /******************************
        required js */

        function makeDraggable(elmnt) {
            let pos1 = 0,
                pos2 = 0,
                pos3 = 0,
                pos4 = 0;

            let dragHandle = elmnt.getElementsByClassName("drag-handle")[0];


            if (dragHandle !== undefined) {
                // if present, the header is where you move the DIV from:
                dragHandle.onmousedown = dragMouseDown;
                dragHandle.ontouchstart = dragMouseDown; //added touch event

            } else {
                // otherwise, move the DIV from anywhere inside the DIV:
                elmnt.onmousedown = dragMouseDown;
                elmnt.ontouchstart = dragMouseDown; //added touch event
            }

            function dragMouseDown(e) {
                e = e || window.event;
                e.preventDefault();
               

                //Get touch or click position
                //https://stackoverflow.com/a/41993300/5078983
                if (e.type == 'touchstart' || e.type == 'touchmove' || e.type == 'touchend' || e.type == 'touchcancel') {
                    let evt = (typeof e.originalEvent === 'undefined') ? e : e.originalEvent;
                    let touch = evt.touches[0] || evt.changedTouches[0];
                    x = touch.pageX;
                    y = touch.pageY;
                } else if (e.type == 'mousedown' || e.type == 'mouseup' || e.type == 'mousemove' || e.type == 'mouseover' || e.type == 'mouseout' || e.type == 'mouseenter' || e.type == 'mouseleave') {
                    x = e.clientX;
                    y = e.clientY;
                }

                console.log("drag start x: "+x+" y:"+y);

                // get the mouse cursor position at startup:
                pos3 = x;
                pos4 = y;
                document.onmouseup = closeDragElement;
                document.ontouchend = closeDragElement;
                // call a function whenever the cursor moves:
                document.onmousemove = elementDrag;
                document.ontouchmove = elementDrag;
            }

            function elementDrag(e) {
                e = e || window.event;
                e.preventDefault();

                //Get touch or click position
                //https://stackoverflow.com/a/41993300/5078983
                if (e.type == 'touchstart' || e.type == 'touchmove' || e.type == 'touchend' || e.type == 'touchcancel') {
                    let evt = (typeof e.originalEvent === 'undefined') ? e : e.originalEvent;
                    let touch = evt.touches[0] || evt.changedTouches[0];
                    x = touch.pageX;
                    y = touch.pageY;
                } else if (e.type == 'mousedown' || e.type == 'mouseup' || e.type == 'mousemove' || e.type == 'mouseover' || e.type == 'mouseout' || e.type == 'mouseenter' || e.type == 'mouseleave') {
                    x = e.clientX;
                    y = e.clientY;
                }

                // calculate the new cursor position:
                pos1 = pos3 - x;
                pos2 = pos4 - y;
                pos3 = x;
                pos4 = y;
                // set the element's new position:
                elmnt.style.top = (elmnt.offsetTop - pos2) + "px";
                elmnt.style.left = (elmnt.offsetLeft - pos1) + "px";
            }

            function closeDragElement() {
                console.log("drag end x: "+pos3+" y:"+pos4);
                // stop moving when mouse button is released:
                document.onmouseup = null;
                document.ontouchcancel = null; //added touch event
                document.ontouchend = null; //added touch event
                document.onmousemove = null;
                document.ontouchmove = null; //added touch event
            }
        }




        /*******************************
        test js */

        makeDraggable(document.getElementById("test-draggable"));
        makeDraggable(document.getElementById("test-draggable2"));
        makeDraggable(document.getElementById("test-full-draggable"));
 /******************************
        required css */

 .draggable {
     position: absolute;
     z-index: 9;
 }

 .drag-handle {
     cursor: move;
     z-index: 10;
 }

 .full-draggable {
     cursor: move;
 }

 /*******************************
        test css */

 .draggable {
     background-color: #f1f1f1;
     border: 1px solid #d3d3d3;
     text-align: center;
 }

 .draggable .drag-handle {
     padding: 10px;
     background-color: #2196F3;
     color: #fff;
 }

 #test-draggable2 {
     left: 200px
 }

 #test-full-draggable {
     left: 500px
 }
 <div id="test-draggable" class="draggable">
        <div class="drag-handle">Drag using me</div>
        I'm the <br>content, <br>you can't<br> drag touching<br> there
    </div>

    <div id="test-draggable2" class="draggable">
        <div class="drag-handle">Drag using me</div>
        It even works with many draggables<br>
        I'm the <br>content, <br>you can't<br> drag touching<br> there
    </div>

    <div id="test-full-draggable" class="draggable full-draggable">


        i don't have <br> a handle so <br> i'm completely <br> draggable
    </div>

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2021-06-18
    • 2021-07-05
    • 2019-06-18
    • 2016-07-29
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-04-27
    相关资源
    最近更新 更多