EdG
EdG

Reputation: 2351

call a function when the value of variable is changed

I am working on react project. I have used videojs player and I am getting the current time of video and I am storing it in a variable "currentTime". Now I have an array of json, each of which has fields startTime and endTime. As the video progresses, I want to check whether my currentTime lies between startTime or endTime of any of the json which are in array. So I want to make a check function for that. As the currentTime changes continuously, I have set an interval of 500 milisec to compare the currentTime with startTime and endTime. Now if say for some "i" (which is some json inside array) the condition of lying in between gets satisfied, I want to store that "i" in my action reducer. As for some time (startTime - endTime) the value of "i" will remain same, I want to call my action creator just one to store this value of "i", and not for the whole time (startTime-endTime).

I have a function which runs on the interval of 500 ms like this

setInterval(function () {
    that.state.tags.map((item, i) => {
        if( item.time <= currentTime && currentTime <= item.stopTime){
            console.log(i);
        }
    }) , 500
})

Now the variable i remains same for sometime (say 5 secs) when the condition gets satisfied for particular currentTime. I have a Redux action creator which should get triggered every time the value of i is changed. Since the value of i gets stored every 500 milliseconds, I cannot call the action creator every 500ms, that too the same value of i. I want to notify or call the action creator when the value of variable i changes. How can I do it? I tried this (below), but this what I mentioned that I don't want to do. markerReachedAction is the action creator I want to call.

setInterval(function () {
    that.state.tags.map((item, i) => {
        if( item.time <= currentTime && currentTime <= item.stopTime){
            that.props.markerReachedAction(i);
            console.log(i);
        }
    }) , 500
})

Upvotes: 0

Views: 105

Answers (1)

T.J. Crowder
T.J. Crowder

Reputation: 1074138

I think you're saying you want to call that.props.markerReachedAction every time the entry in that.state.tags where item.time <= currentTime && currentTime <= item.stopTime changes (e.g., time has moved on, and now instead of entry 0 matching, it's entry 1).

If so, as Jordan said, setInterval is probably not the right tool. But without more context, it's hard to point you in the right direction.

In terms of getting it working with setInterval, you need to remember the last value of the matching index. Also, map is the wrong tool to use to just loop through an array (it builds a new array). To just loop, use forEach; but in your case, you want to stop looping when the condition is reached. Normally, that would be some (just generally stopping when you reach a condition), find (finding a specific entry in the array based on callback), or findIndex (finding the index of a specific entry in the array based on a callback). In your case, findIndex:

let lastNotifiedIndex = -1; // -1 won't match any array index, so we'll fire the first time
setInterval(function() {
    // Find the index for which our predicate function returns true
    const index = that.state.tags.findIndex(item => item.time <= currentTime && currentTime <= item.stopTime);

    // If we found one, is it different?
    if (index !== -1 && lastNotifiedIndex !== index) {
        // Yes, notify
        lastNotifiedIndex = index;
        that.props.markerReachedAction(lastNotifiedIndex);
    }
}, 500);

I assume something, somewhere, is updating currentTime? If not, you probably want to update it at the beginning of the timer callback.

Upvotes: 1

Related Questions