Loop through layers

4782
4
Jump to solution
04-13-2015 09:34 AM
CharlesGant
New Contributor III

All,

I have what seems like a simple request, although it is apparently not.

i have a map div that contains a series of check boxes that represent layer ids.  When a box is checked, an array is created and all checked boxes thus layer ids are added to the array.  I now need to loop through the array, and turn on the first layer, wait some amount of time, turn that layer off, move to the next layer in the array and repeat, indefinitely.  Only when a layer is added, or removed from the array would the loop restart.  Below is what I have tried.  But it doesn't work.

//Sleep Function

function sleep(milliseconds) {

    var start = new Date().getTime();

    for (var i = 0; i < 1e7; i++) {

    if ((new Date().getTime() - start) > milliseconds){

    break;

        }

    }

}

          

//Layer Looper Function

function startLoop(visibleLayerIds) {

for (var t = 0; t < layers.length; t++) {

    layername = layers.id

    // console.log(layername);

    if ($.inArray(layername, visibleLayerIds) > -1) {

    console.log(layername + " set to visible");

    layers.show();

    sleep(30000);

    layers.hide();

    console.log(layername + " set to invisible");

        }

    }

}

          

//Update Layer Visibility Function

on(dom.byId("layer0CheckBox"), "change", updateLayerVisibility);

on(dom.byId("layer1CheckBox"), "change", updateLayerVisibility);

          

function updateLayerVisibility () {

    var inputs = query(".list_item");

    var inputCount = inputs.length;

    var visibleLayerIds = []

    //Get Checked Layers

    for (var i = 0; i < inputCount; i++) {

    if (inputs.checked) {

    visibleLayerIds.push(inputs.value);

    }

}

startLoop(visibleLayerIds);

}

Tags (1)
0 Kudos
1 Solution

Accepted Solutions
BrentHoskisson
Occasional Contributor III

As you have it written, both timeouts for all layers will be run at the same time, as you found out.

Your startLoop will need to grab only the first layer in the array and start the showLayers timer.  Then, your showLayers function will need to start your timer for the hideLayers function.   Finally, your hideLayers function will need to increment your layer index, grab the next layer in the array and start the timer for the showLayers function again (or successfully exit if you are beyond the layer array range).

This way you will only have one timer running at a time.

View solution in original post

4 Replies
BrentHoskisson
Occasional Contributor III

You do not want to "sleep".  That stops everything including the refresh of the map.  You will want to look at timers.  Start with this document:

JavaScript Timing Events

Good Luck

Brent

0 Kudos
CharlesGant
New Contributor III

Brent,

Thanks for the response.  I have worked the setTimeout function into the code, however I think I'm having another issue.  It seems that the function containing the two 'timeouts' is continuing through the loop before waiting for the two 'timeouts' to complete.  An asynchronous issue perhaps?  Still kinda new to JS, but I read that I need to add callbacks.  However I'm not sure where to do that in my code snippet.  Any advice?

function showLayers(templayer) {

console.log("here");

templayer.show();

}

function hideLayers(templayer) {

console.log("here");

templayer.hide();

}

//Layer Looper Function

function startLoop(visibleLayerIds) {

for (var t = 0; t < layers.length; t++) {

    layername = layers.id

    // console.log(layername);

    if ($.inArray(layername, visibleLayerIds) > -1) {

    console.log(layername + " set to visible");

    setTimeout(showLayers, 5000,layers);

    setTimeout(hideLayers, 15000,layers);

        }

    }

}

//Update Layer Visibility Function

on(dom.byId("layer0CheckBox"), "change", updateLayerVisibility);

on(dom.byId("layer1CheckBox"), "change", updateLayerVisibility);

function updateLayerVisibility () {

    var inputs = query(".list_item");

    var inputCount = inputs.length;

    var visibleLayerIds = []

    //Get Checked Layers

    for (var i = 0; i < inputCount; i++) {

    if (inputs.checked) {

        visibleLayerIds.push(inputs.value);

        }

    }

    startLoop(visibleLayerIds);

}

0 Kudos
BrentHoskisson
Occasional Contributor III

As you have it written, both timeouts for all layers will be run at the same time, as you found out.

Your startLoop will need to grab only the first layer in the array and start the showLayers timer.  Then, your showLayers function will need to start your timer for the hideLayers function.   Finally, your hideLayers function will need to increment your layer index, grab the next layer in the array and start the timer for the showLayers function again (or successfully exit if you are beyond the layer array range).

This way you will only have one timer running at a time.

CharlesGant
New Contributor III

Brent,

After following your suggestions, I "think" I got it figured out.  Your guidance is much appreciated!

Charles

0 Kudos