Scrolling vertically at regular intervals of 5 seconds

I am experimenting with creating a vertical scrolling animation.

Within a div, I have 9 elements with overflow hidden, allowing only 3 elements to be visible at once.

Every 5 seconds, I aim to add styles to the elements using negative margin-top values and adjusting the orderStep variable. For example, when orderStep is 1, I set the margin-top to 0; for 2, -190px; and for 3, -380px.

I have defined a function within the methods object to handle this which I call on created after fetching records from the backend.

Unfortunately, my current implementation isn't working correctly:


        // Vue object data method
         data() {
             return {
                 articles: [],
                 errors: [],
                 step: 1
             }
         },
         methods: {
            changeSlide() {
                const elements = document.querySelectorAll('.most__popular');
                setInterval(() => {
                    switch (this.step) {
                        case 1:
                            for(let val of elements) {
                                val.style.margin = "10px 0";
                            }
                            this.step = 2;
                            break;
                        case 2:
                            for(let val of elements) {
                                val.style.margin = "-190px 0 0 0";
                            }
                            this.step = 3;
                            break;
                        case 3:
                            for(let val of elements) {
                                val.style.margin = "-380px 0 0 0";
                            }
                            this.step = 1;
                            break;
                    }
                },5000);
            }
        },
        async created() {
            try {
                const response = await axios.get(`/api/article/getMostPopular.php`, axiosConfig);
                this.articles = response.data.records;
                this.changeSlide();
            } catch (e) {
                this.errors.push(e)
            }
        },
    

After some debugging, it turns out that the NodeList returned by document.querySelectorAll is empty, likely because I'm referencing elements rendered asynchronously through v-for below my axios.get request. How can I resolve this issue?

Following RoyJ's recommendation, I'm now binding styles using the :style directive in the template:


            <div class="most__popular"
                 v-for="n in articles" :key="n.id"
                 :style="{margin: sliderMargin}">
    

The margin value is controlled by the sliderMargin variable updated in my function:


    changeSlide() {
        setInterval(() => {
            switch (this.step) {
                case 1:
                    console.log('step1');
                    this.sliderMargin = '10px 0 0 0';
                    this.step = 2;
                    break;
                case 2:
                    console.log('step2');
                    this.sliderMargin = '-190px 0 0 0';
                    this.step = 3;
                    break;
                case 3:
                    console.log('step3');
                    this.sliderMargin = '-190px 0 0 0';
                    this.step = 1;
                    break;
            }
        },5000);
    }
    

However, this approach applies the margin to all elements causing them to disappear instead of scrolling. To achieve the desired result:

  • On the first step, apply margin-top: 10px to all elements
  • On the second step, apply -190px margin-top to elements 1, 2, and 3, while the rest have 10px
  • On the third step, apply -190px margin-top to elements 1-6, while the rest have 10px

How can I adjust the :style directive to target only the first three elements if this.step is equal to 2, or six elements if this.step is equal to 3, and none if this.step is equal to 1?

Answer №1

When using the setInterval function, there is no need to test the value of this.step; instead, simply update its value. The function employs modulo arithmetic to iterate through values of 0, 1, 2.

A computed property is created to calculate the margin for each article based on its index (ranging from 0 to 5) and the value of this.step. Consequently, sliderMargin becomes an array with one element corresponding to each item in the articles array. Within the v-for loop, the relevant element from sliderMargin is used for each article.

The array thresholds specifies how many articles will have a 10px margin versus a -190px margin for each step.

new Vue({
  el: '#app',
  data: {
    articles: [1,2,3,4,5,6],
    step: 0
  },
  computed: {
    sliderMargin() {
      const thresholds = [0, 3, 6];

      return this.articles.map((_, i) =>
        `${(i < thresholds[this.step]) ? '10px' : '-190px'} 0 0 0`
      );
    }
  },
  mounted() {
    setInterval(() => {
      this.step = (this.step + 1) % 3;
    }, 5000);
  }
});
<script src="//unpkg.com/vue@latest/dist/vue.js"></script>
<div id="app">
  <div class="most__popular" v-for="n, i in articles" :key="n.id" :style="{margin: sliderMargin[i]}">
    {{n}}
  </div>
</div>

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

Update information in a table row and store it in the database using Ajax

Looking for some guidance with ajax and javascript here. I'm not very proficient in this area, so any help would be greatly appreciated. I have a table on my page where data is displayed like this: <table class="table table-bordered"> ...

When you try to upload an image using php/ajax, it causes the page to refresh

I'm currently experiencing an issue with my script. I am successfully using formData() to upload an image via Ajax, which is being saved to the designated folder. However, I am puzzled as to why my page keeps refreshing after move_uploaded_file() is e ...

Steps to trigger a Bootstrap modal when the user clicks anywhere on the webpage

I need assistance with setting up a Bootstrap dialogue modal to open at the clicked position on a mousedown event when a user interacts with the page. Despite my attempts, the dialogue modal is not opening where it should be. Here's what I've tri ...

Troubleshooting a Custom Menu Control in HTML

Would you mind taking a look at the menu I have set up in this fiddle: http://jsfiddle.net/Gk_999/mtfhptwo/3 (function ($) { $.fn.menumaker = function (options) { var cssmenu = $(this), settings = $.extend({ title: "Menu", ...

Unpacking Objects in JavaScript and TypeScript: The Power of Destructuring

I have a variable called props. The type includes VariantTheme, VariantSize, VariantGradient, and React.DOMAttributes<HTMLOrSVGElement> Now I need to create another variable, let's name it htmlProps. I want to transfer the values from props to ...

Evaluating the similarity between a Guild ID and a matching string

Currently, I am in the process of creating a bot with a unique feature - a config command that enables users to customize specific functionalities within their servers. This customization is facilitated through a straightforward JSON file named config.json ...

Create an Angular service that outputs class properties as observables

I am trying to accomplish the following task: I have a component with a UserService in it. After a user logs in, I want to call this service to retrieve user data from the backend and store it in a service field. Then, when the main page is reloaded, I wan ...

The console is showing messages before the task is completed

When using console.log to write detailed messages about the current task expected to be performed by Protractor, I noticed that these messages are appearing on the console before the actual task is executed in the browser. An example of this is: it(' ...

Implementing yadcf and a fixed column filter in a Bootstrap datatable

I am currently utilizing Bootstrap DataTable in conjunction with the Yadcf filter plugin. The filter is functioning correctly for a regular table, however, when I have a fixed column with a Select2 dropdown, it does not render properly. The dropdown is hid ...

How to retrieve scope variable within the <script> element

I have a question about using angularjs. Here is the structure of my HTML: <html> <body ng-controller="datafileController"> <div class="container"> <center><h1>Datafiles</h1></center> ...

Guide to utilizing axios.request(config) in Vue.js

I have been attempting to use Axios in my vue.js project to make HTTP requests. Despite reviewing the Axios documentation on GitHub and exploring various examples online, I have yet to find a solution. My goal is to create a configuration file where I can ...

Grouping JavaScript nested properties by keys

I have a specific object structure in my code that I need to work with: { "changeRequest": [{ "acrId": 11, "ccrId": "", "message": "test message" }, ...

When using the ajax method to pass data from the view to the controller, I encountered an issue where the data would unexpectedly become null once it reached the action

function UserLogin() { var username = $("#txtUsername").val(); var passcode = $("#txtPassword").val(); alert(username); $.ajax({ url: '@Url.Action("Login", "UserAccount")', ...

Differences in window height between Firefox and Chrome

When positioning a modal vertically, how can I ensure consistent alignment across different browsers? method.center = function () { var top, left; top = Math.max($(window).height() - $modal.outerHeight(), 0) / 2; left = Math.max($(window).widt ...

Exploring the functionality of dimensions in d3 parcoords

I am diving into the world of d3 and experimenting with Behold, a simplistic example directly from the website. <script src="http://d3js.org/d3.v3.min.js"></script> <script src="d3.parcoords.js"></script> <link rel="stylesheet" ...

JavaScript does not recognize the $ symbol

Firebug is indicating that there is an issue with the $ variable not being defined. I have a basic index.php page that uses a php include to bring in the necessary content. The specific content causing the error is shown below: <script type="text/jav ...

avoiding the initiation of a new ajax request while a previous one is still in progress

Attempting to create a function that retrieves data from a server on scroll. The function would look something like this... function onscrollend() { $.ajax({ }); } Feeling a bit perplexed about how to verify if the old .ajax() call is still in pr ...

Embracing unconventional attributes within AngularJS

After converting my model from Java to JavaScript using GWT 2.7, I have a set of properties with getValue() and setValue() methods that are not obfuscated. I am interested in using these properties in {{}} expressions, especially for data binding with ngM ...

Is there a way for me to attach a link to a picture displayed in a lightbox that directs to an external ".html" file?

I have a platform where users can view images in a gallery and when they click on an image, it opens up in a lightbox. I am trying to add a feature where the opened image can be clicked again to redirect the user to an external page. I attempted to nest t ...

A simple guide on integrating personalized color palettes into Material-UI Theme

One enhancement I'd like to make in my theme is the inclusion of a custom color called warn import React from 'react' import { MuiThemeProvider } from '@material-ui/core/styles' import createMuiTheme from '@material-ui/core/s ...