小能豆

Is this the correct way of reusing a JS function?

javascript

I have a two functions written that works great. One function will add the HTML video attribute autoplay to the video DOM element, if the user is at a certain section on the page. Another function will slide in some elements with a nice transition.

But the downside is that it will work for one element within page, but I would like to have it work on other elements as well.

Here is one function, the one that play the video on scroll:

playOnScroll: function() {

    var player = $('.browser video');
    var hasReached = false;

    function isInView(elem){
        return $(elem).offset().top - $(window).scrollTop() < $(elem).height();
    }

    $(window).scroll(function() {

        var section = $('#user-experience');

        // If section exists
        if (section.length) {

            if (isInView(section) && !hasReached) {
                // console.log('play video');
                hasReached = true;
                player.get(0).play();
            }

        }

    });

}

For now the function does only the work if the section with the id #user-experience is in view, but it would be great if I can use the function for more sections.

At the moment of writing, I am thinking about to change the target section to a classname and if a section has this class it will do its work. Or is there some better way to do this?

If I take a look at my second function that I mentioned before, that will handle some nice incoming animation on scroll, I doesn’t know how to reuse this function for multiple element selectors:

moduleShift: function() {

    var root = this;
    var el = $('.entry figure');
    var offset = 0.8;

    root.isVisible(el, offset);

    $(window).scroll(function() {

        // Get the offset of the window from the top of page
        var windowPos = $(this).scrollTop();

        setTimeout(function(){ 
            root.isVisible(el, offset); 
        }, 1000);

    });

}, 

isVisible: function(el, offset) {

    el.each(function() { 
        var elHeight = $(this).outerHeight();
        var offsetTop = $(this).offset().top;
        var offsetBottom = offsetTop + elHeight;

        if (offsetTop <= $(window).scrollTop() + $(window).height()*offset) {
            $(this).addClass('moduleShift');
        };

    });

}

The same solution for above should be able to apply also to this function, but maybe the same question as for the first function, is there a better way to do this?


阅读 91

收藏
2023-12-02

共1个答案

小能豆

For both of your functions, the idea of making them more reusable and applicable to multiple elements is a good approach. Here are some suggestions:

For the Video Autoplay Function:

  1. Use a Class Selector: Instead of selecting elements by ID, use a class selector. This way, you can apply the same logic to multiple elements on the page.

```
playOnScroll: function() {
var players = $(‘.autoplay-video’);

   function isInView(elem) {
       // ...
   }

   $(window).scroll(function() {
       players.each(function() {
           if (isInView($(this)) && !$(this).data('hasReached')) {
               $(this).data('hasReached', true);
               $(this).get(0).play();
           }
       });
   });

}
```

And in your HTML, add the class to the video elements you want to apply this behavior to:

<video class="autoplay-video" controls> <!-- Your video source and other attributes --> </video>

For the Animation Function:

  1. Use a Class Selector: Similar to the first function, use a class selector for elements you want to animate. This allows you to reuse the same animation logic for different sets of elements.

```
moduleShift: function() {
var elements = $(‘.animate-on-scroll’);
var offset = 0.8;

   root.isVisible(elements, offset);

   $(window).scroll(function() {
       setTimeout(function() {
           root.isVisible(elements, offset);
       }, 1000);
   });

},

isVisible: function(elements, offset) {
elements.each(function() {
var elHeight = $(this).outerHeight();
var offsetTop = $(this).offset().top;
var offsetBottom = offsetTop + elHeight;

       if (offsetTop <= $(window).scrollTop() + $(window).height() * offset) {
           $(this).addClass('moduleShift');
       }
   });

}
```

Add the class to the elements you want to animate:

<div class="animate-on-scroll"> <!-- Your content --> </div>

By using class selectors and making the functions more generic, you make them adaptable for various elements on your page.

2023-12-02