2018年1月24日 星期三

javascript drag 實作

實作在 jquery ui 中的  draggble
單純懶得為了只需要一個功能
就引入一個檔案
看起來也不是很難
所以就自己做看看



思維:

滑鼠點選物件 -> mousedown
滑鼠移動 -> mousemove
滑鼠放開 -> mouseup

開始:

        var x = 0 , y = 0;
        var move_x = 0, move_y = 0;
        var moving = false;
        var start_x = 0, start_y = 0;

        var style = window.getComputedStyle(element);
     
        var features = {
            start: function (ui) {},
            drag: function (ui) {},
            end: function (ui) {},
            axis: "s"
        };




假設物件的 top 和 left 皆為 20
物件寬高為 100px * 100px

x , y 是按下的物件的內部位置  和 物件位置的和
start_x  , start_y  是被滑鼠按下物件本身的位置
之所以需要這兩樣數值是為了當拖曳時
滑鼠能維持在物件本身的位置

move_x , move_y  是當滑鼠移動的物件的新位置
moving  物件是否在移動中

style 取得物件的位置資料
features 在各種情況下的行為
axis 設為 y  只能上下移動    設為 x  只能 左右移動

var ui = {
            regex: /[-0-9]*/
          
            ,regexValue:function(value)
            {
                value = value.match(ui.regex);
                if(value == "")
                    return 0;
                return parseInt(value);
            }
            ,top: function (val) {
              
              
                if (val === undefined)
                {
                    var t = style.getPropertyValue('top').toString();                 
                    return  ui.regexValue(t);
                }
                element.style.top = val + "px";
            }
            ,left: function (val) {
              
                if (val === undefined)
                {
                    var t = style.getPropertyValue('left').toString();               
                    return  ui.regexValue(t);                 
                }
                element.style.left = val + "px";
            }
        };

這段只是要取得
top 和 left 的 值
和 設定 top 和 left

ui.top() -> 傳回 top
ui.top(10) -> 設定 top

運作:




最主要就是要滑鼠移動也讓物件移動
所以如何計算新的位置就是重點

開始:
extend();
element.addEventListener("mousedown", function (event) {

                x = event.clientX;
                y = event.clientY;
                start_x = ui.left();
                start_y = ui.top();
                moving = true;
                features.start(ui);

            });
            function extend()
            {
                for (var key in func)
                {
                    features[key] = func[key];
                }
            }
將需要的資料存好
moving 設為 true
features.start(ui);   開始的動作

滑鼠移動:

            element.addEventListener("mousemove", function (event) {
                if (moving) {
                    moveValue(event);
                    move();
                    features.drag(ui);
                }
            });
            window.addEventListener("mousemove", function (event) {
                if (moving) {
                    moveValue(event);
                    move();
                    features.drag(ui);
                }
            });
            function moveValue(event)
            {
                move_x = event.clientX - x + start_x;
                move_y = event.clientY - y + start_y;
            }

            function move()
            {
                if(features.axis=="y" || features.axis=="s")
                   ui.top(move_y);
                if(features.axis=="x" || features.axis=="s")
                   ui.left(move_x);
            }

移動後就計算新位置
並更新位置

window 也要添加事件是因為
滑鼠如果移動太快
會移出物件範圍
如果window也有添加  就解決這問題

結束:

            element.addEventListener("mouseup", function (event) {
                features.end(ui);
                moving = false;
            });
            window.addEventListener("mouseup", function (event) {
                features.end(ui);
                moving = false;
            });

將 moving = false


沒有留言:

張貼留言