Search code examples
javascriptmethodsinstanceinvoke

Why another instance method call doesn't run?


In my JavaScript, I have a move() method for the Image class, which is supposed to animate the instances of the Image class, when their move() method is called, with the argument of their numeric ids,

the first time, the method Image1.move(1); is called and it animates the first Image instance, in the move() method, however, I have declared the next instance to run the move() method with the argument of it's id, but except for the instance Image1, no other instances run the move() method called for, why does that happen? And how do I make other instances to run move() method, when being called?

document.addEventListener('DOMContentLoaded', function (event) {
        let slidingChoices = {
            slideCount: 3,
            slidingDuration: 1000,
            slidePause: 2500,
        }
        let sliderWrapper = document.getElementsByClassName('slider-wrapper')[0];
        let sliderWrapperWidth = sliderWrapper.offsetWidth;
        class Image {
            constructor(_src, _id) {
                this.src = _src;
                this.id = _id;
                this.appear()
            }
            appear() {
                let img = document.createElement('img');
                img.setAttribute("src", this.src);
                img.id = this.id;
                img.classList.add('img');
                sliderWrapper.appendChild(img);
                img.style.left = `${sliderWrapperWidth}px`;
                img.onload = function() {
                    sliderWrapper.style.height = `${img.height}px`;
                }
                document.getElementById('1').style.left = '0';
            }
            move(which) {
                let NextImageNumber;
                window.onload = function() {  document.getElementById(which).style.left = '0px';
                    document.getElementById(which).style.transition =  slidingChoices.slidingDuration + 'ms';
                    if (document.getElementById(which).style.left === '0px') {
                        setTimeout(function () {
                            document.getElementById(which).style.left = -sliderWrapperWidth + 'px';
                            document.getElementById(which).style.transition = slidingChoices.slidingDuration + 'ms';  document.addEventListener('transitionend', () => {
                                document.getElementById(which).style.left = sliderWrapperWidth + 'px';
                                document.getElementById(which).style.transition = 'none';
                            });
                            // Here is the problem
                            NextImageNumber = (which + 1 < slidingChoices.slideCount ) ? which + 1 : 1;
                            eval(`Image${NextImageNumber}.move(${NextImageNumber})`);
                        },slidingChoices.slidePause)
                    }
                }
            }
        }
        for (let i = 1; i <= slidingChoices.slideCount; i++) {
            eval(`Image${i} = new Image('https://via.placeholder.com/200/FFFF00/000000?Text=WebsiteBuilders.com', '${i}')`);
        }
        Image1.move(1);

    });
*{
            padding: 0;
            margin: 0;
            -webkit-box-sizing: border-box;
            -moz-box-sizing: border-box;
            box-sizing: border-box;
        }
        .slider-wrapper{
            position: relative;
            max-width: 200px;
            margin: 50px auto;
            box-sizing: content-box;
            border: 1px solid #000;
        }
        .slider-wrapper img{
            position: absolute;
            display: block;
        }
<div class="slider-wrapper">
</div>


Solution

  • Image is the name of a built in JS class, and in strict mode eval won't have access to your overwritten class, so it's calling the native image class instead of the one you defined and the native one doesn't have a move method. You should probably rename your class.

    Also, window.onload isn't going to be called every time you call move(). That should be at the top level, not inside your move method.