Search code examples
javascriptjquerymouseevent

Detect mouseMove of X pixels


I'm trying to trigger an event when the cursor position moves X amount of pixels, say 100px. So, for every 100px the cursor moves in either X or Y direction, I trigger an event. This should continue for every 100px movement.

I've successfully detected the 'current' X and Y position of the cursor, and have set a pixel threshold, but am struggling with the maths on the rest. Can anyone help?

$(window).on('mousemove', function(e){

    // Vars
    var cursorX = e.clientX;
    var cursorY = e.clientY;
    var cursorThreshold = 100;

    ... detect every 100px movement here...

});

Solution

  • You need to keep track of the old cursor positions. Then you can calculate the distance using the Pythagorean theorem:

    totalDistance += Math.sqrt(Math.pow(oldCursorY - cursorY, 2) + Math.pow(oldCursorX - cursorX, 2))
    

    This works in any direction.

    Example:

    Note: Unlike @wayneOS's approach (+1 from me) I do not keep track of the direction.
    It's a rather minimalistic implementation.

    var totalDistance = 0;
    var oldCursorX, oldCursorY;
    
    $(window).on("mousemove", function(e){
        var cursorThreshold = 100;
        
        if (oldCursorX) totalDistance += Math.sqrt(Math.pow(oldCursorY - e.clientY, 2) + Math.pow(oldCursorX - e.clientX, 2));
        if (totalDistance >= cursorThreshold){
            console.log("Mouse moved 100px!");
            totalDistance = 0;
        }
        
        oldCursorX = e.clientX;
        oldCursorY = e.clientY;
    });
    .d {
        width: 0;
        height: 0;
        border-style: solid;
        border-width: 100px 100px 0 0;
        border-color: #e54646 transparent transparent transparent;
    }
    .s { display: flex; }
    .p1 { margin-left: 100px; }
    .p2 { margin-right: 20px; padding-top: 20px; }
    <script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
    <p class="p1">100px X</p>
    <div class="s">
        <p class="p2">100px Y</p>
        <div class="d"></div>
    </div>