JavaScript函数,与函数参数关联的错误

时间:2018-11-19 06:10:15

标签: javascript function parameters slider

我很抱歉,这个问题很难表达,标题可能会误导他人。这个问题基本上与将参数传递给JavaScript中的函数有关。

下面的这些代码是一项允许元素水平移动的功能。在滑块中使用。我的问题与我评论的两行有关。

我在一个名为 common.js 的单独的.js文件中编写了以下函数,并且效果很好:

(请注意我评论的两行内容)

function animateX(element, target, stepWidth) {     // the stepWidth parameter
    clearInterval(element.timerId);
    element.timerId = setInterval(function () {
        var current = element.offsetLeft;
        var step = stepWidth;                       // This line
        step = current < target ? step : -step;
        current += step;
        if (Math.abs(target - current) > Math.abs(step)) {
            element.style.left = current + "px";
        } else {
            clearInterval(element.timerId);
            element.style.left = target + "px";
        }
    }, 10);
}

但是,如果我以这种方式编写它,则会出现一个错误:

过渡消失了,当我单击箭头时,图片立即移动到目标,而不是滑动到目标。

function animateX(element, target, step) {     // the parameter uses the same name as the local variable
    clearInterval(element.timerId);
    element.timerId = setInterval(function () {
        var current = element.offsetLeft;
        var step = step;                       // This line: stepWidth -> step
        step = current < target ? step : -step;
        current += step;
        if (Math.abs(target - current) > Math.abs(step)) {
            element.style.left = current + "px";
        } else {
            clearInterval(element.timerId);
            element.style.left = target + "px";
        }
    }, 10);
}  

此外,如果我以这种方式编写,情况会变得更糟:

图片不会按计划移动,会先移动一点然后颤抖。

function animateX(element, target, step) {          // This line
    clearInterval(element.timerId);
    element.timerId = setInterval(function () {
        var current = element.offsetLeft;
       // Now I understand why this one is wrong.
        // I changed it to step = current < target ? Math.abs(step) : -Math.abs(step);
        // Problem solved.
        step = current < target ? step : -step;
        current += step;
        if (Math.abs(target - current) > Math.abs(step)) {
            element.style.left = current + "px";
        } else {
            clearInterval(element.timerId);
            element.style.left = target + "px";
        }
    }, 10);
}

我完全认为这三种方式是相同的,但是它们给我带来了完全不同的结果。

我还认为第三种方法更好,因为它的行数更少。但是,它不起作用。

有人可以告诉我区别吗?我真的很感激!

下面是html代码,如果您有时间,只需复制并尝试即可。这个html文件和js函数是您工作所需的全部。您可以看到没有图片的区别。

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
    <style type="text/css">
        * {
            margin: 0;
            padding: 0
        }

        ul {
            list-style: none
        }

        img {
            vertical-align: top;
        }

        .box {
            width: 960px;
            height: 540px;
            margin: 100px auto;
            padding: 5px;
            border: 1px solid #ccc;
        }

        .inner {
            width: 960px;
            height: 540px;
            background-color: pink;
            overflow: hidden;
            position: relative;
        }

        .inner ul {
            width: 1000%;
            position: absolute;
            top: 0;
            left: 0;
        }

        .inner li {
            float: left;
        }

        #imgs li a {
            width: 960px;
            height: 540px;
            display: block;
        }

        #focusD {
            display: none;
        }

        #focusD span {
            position: absolute; /* inner是relative */
            width: 40px;
            height: 40px;
            left: 5px;
            top: 50%;
            margin-top: -20px;
            background: #000;
            font-family: arial, sans-serif;
            cursor: pointer;
            line-height: 40px;
            text-align: center;
            font-weight: bold;
            font-size: 30px;
            color: #fff;
            opacity: 0.3;
            border: 1px solid #fff;
        }

        #focusD #right {
            right: 5px;
            left: auto;
        }

    </style>
</head>
<body>
<div class="box" id="box">
    <div class="inner">
        <ul id="imgs">
            <li><a href="#"><img src="images/d1.jpg" alt="d1"/></a></li>
            <li><a href="#"><img src="images/d2.jpg" alt="d2"/></a></li>
            <li><a href="#"><img src="images/d3.jpg" alt="d3"/></a></li>
            <li><a href="#"><img src="images/d4.jpg" alt="d4"/></a></li>
            <li><a href="#"><img src="images/d5.jpg" alt="d5"/></a></li>
        </ul>
        <div id="focusD">
            <span id="left">&lt;</span>
            <span id="right">&gt;</span>
        </div>
    </div>
</div>

<script type="text/javascript" src="common.js"></script>
<script type="text/javascript">
    // getElementByID
    function my$(id) {
        return document.getElementById(id);
    }
</script>
<script type="text/javascript">
    var box = my$("box");
    // get slider frame
    var inner = box.children[0];
    // get frame width
    var imgWidth = inner.offsetWidth;
    // get ul
    var ulObj = inner.children[0];
    // get div containing arrows
    var focusD = my$("focusD");

    // show / hide arrows
    box.onmouseover = function () {
        focusD.style.display = "block";
    };
    box.onmouseout = function () {
        focusD.style.display = "none";
    };

    var index = 0;
    // click left arrow
    my$("left").onclick = function () {
        if (index > 0) {
            index--;
            animateX(ulObj, -index * imgWidth, 20);
        }
    };
    // click right arrow
    my$("right").onclick = function () {
        if (index < ulObj.children.length - 1) {
            index++;
            animateX(ulObj, -index * imgWidth, 20);
        }
    };

</script>
</body>
</html>

1 个答案:

答案 0 :(得分:0)

在函数的第二次迭代中,创建一个名为“ step”的变量,该变量与函数参数之一相同。在第三次迭代中,您并未创建函数正常工作所需的“ stepWidth”副本。尝试创建一个具有不同名称的变量来存储“ step”的副本。

function animateX(element, target, step) {         
clearInterval(element.timerId);
element.timerId = setInterval(function () {
    var current = element.offsetLeft;
    var stepWidth = step;                          
    stepWidth = current < target ? stepWidth : -stepWidth;
    current += stepWidth;
    if (Math.abs(target - current) > Math.abs(stepWidth)) {
        element.style.left = current + "px";
    } else {
        clearInterval(element.timerId);
        element.style.left = target + "px";
    }
}, 10);

}