cmv / cmv-app

CMV - The Configurable Map Viewer - A community supported open source mapping framework built with the Esri JavaScript API and the Dojo Toolkit
https://demo.cmv.io/
MIT License
325 stars 278 forks source link

LayerControl check perant box #336

Closed goriliukasbuxton closed 9 years ago

goriliukasbuxton commented 9 years ago

Hello, I would like to turn on group layer and map server check box (all layer parents) if child layer is clicked. Any help would be appreciated.

akakruger commented 9 years ago

Hi, I've manage to CHECK ON group layers and the map service when a child layer is CHECKED ON. I'm new to the code, so please do improve it where you can. Look for //AK tags in the code. Updates in _DynamicSublayer.js , _DynamicFolder.js and LayerControl.js

snippet from LayerControl.js

.
.
.
.
        postCreate: function () {
            this.inherited(arguments);
            if (this.separated) {
                var ControlContainer = declare([WidgetBase, Container]);
                // vector layer label
                if (this.vectorLabel !== false) {
                    this.addChild(new ContentPane({
                        className: 'vectorLabelContainer',
                        content: this.vectorLabel
                    }, domConst.create('div')), 'first');
                }
                // vector layer control container
                this._vectorContainer = new ControlContainer({
                    className: 'vectorLayerContainer'
                }, domConst.create('div'));
                this.addChild(this._vectorContainer, 'last');
                // overlay layer label
                if (this.overlayLabel !== false) {
                    this.addChild(new ContentPane({
                        className: 'overlayLabelContainer',
                        content: this.overlayLabel
                    }, domConst.create('div')), 'last');
                }
                // overlay layer control container
                this._overlayContainer = new ControlContainer({
                    className: 'overlayLayerContainer'
                }, domConst.create('div'));
                this.addChild(this._overlayContainer, 'last');
            } else {
                this.overlayReorder = false;
                this.vectorReorder = false;
            }
            // load only the modules we need
            var modules = [];
            // push layer control mods
            array.forEach(this.layerInfos, function (layerInfo) {
                // check if control is excluded
                var controlOptions = layerInfo.controlOptions;
                if (controlOptions && controlOptions.exclude === true) {
                    return;
                }
                var mod = this._controls[layerInfo.type];
                if (mod) {
                    modules.push(mod);
                } else {
                    topic.publish('viewer/handleError', {
                        source: 'LayerControl',
                        error: 'the layer type "' + layerInfo.type + '" is not supported'
                    });
                }
            }, this);
            // load and go
            require(modules, lang.hitch(this, function () {
                array.forEach(this.layerInfos, function (layerInfo) {
                    // exclude from widget
                    var controlOptions = layerInfo.controlOptions;
                    if (controlOptions && controlOptions.exclude === true) {
                        return;
                    }
                    var control = this._controls[layerInfo.type];
                    if (control) {
                        require([control], lang.hitch(this, '_addControl', layerInfo));
                    }
                }, this);
                this._checkReorder();
            }));
            //AK start
            this._layerONOFFHandle = topic.subscribe('layerControl/layerON', lang.hitch(this, function (lyr) {
             this.showLayer(lyr.layerId);
            }));
            //AK end
        },
        //AK start
        //loop through layers and switch on if layerId match.
        showLayer: function (layerId) {
            array.forEach(this._vectorContainer.getChildren(), function (child) {
                if (child.layer.id === layerId)
                        child.layer.show();
                });
            array.forEach(this._overlayContainer.getChildren(), function (child) {
                if (child.layer.id === layerId)
                    child.layer.show();
                });
        },//AK end
.
.
.
.

snippet from _DynamicFolder.js

define([
    'dojo/_base/declare',
    'dojo/_base/lang',
    'dojo/_base/array',
    'dojo/on',
    'dojo/topic', //AK Added
    'dojo/dom-class',
    'dojo/dom-style',
    'dojo/dom-attr',
    'dojo/html',
    'dijit/_WidgetBase',
    'dijit/_TemplatedMixin',
    'dojo/text!./templates/Folder.html'
], function (
    declare,
    lang,
    array,
    on,
    topic, //AK added
    domClass,
    domStyle,
    domAttr,
    html,
    WidgetBase,
    TemplatedMixin,
    folderTemplate
) {
.
.
.
.
postCreate: function () {
            this.inherited(arguments);
            var checkNode = this.checkNode;
            domAttr.set(checkNode, 'data-sublayer-id', this.sublayerInfo.id);
            domAttr.set(checkNode, 'data-sublayer-parent-id', this.sublayerInfo.parentLayerId);  //AK added
            domClass.add(checkNode, this.control.layer.id + '-layerControlSublayerCheck');
.
.
.
.
// set checkbox based on layer so it's always in sync
        _setSublayerCheckbox: function (checked, checkNode) {
            checkNode = checkNode || this.checkNode;
            var i = this.icons;
            if (checked) {
                domAttr.set(checkNode, 'data-checked', 'checked');
                domClass.replace(checkNode, i.checked, i.unchecked);
                //AK added
                if (domAttr.get(checkNode, 'data-sublayer-parent-id') === "-1") {
                    topic.publish('layerControl/layerON', {
                        layerId: this.control.layer.id
                    });
                }
              //AK end
            } else {

                domAttr.set(checkNode, 'data-checked', 'unchecked');
                domClass.replace(checkNode, i.unchecked, i.checked);
            }
        },
.
.
.
.

snippet from _DynamicSublayer.js

define([
    'dojo/_base/declare',
    'dojo/_base/lang',
    'dojo/_base/array',
    'dojo/on',
    'dojo/dom-class',
    'dojo/dom-style',
    'dojo/dom-attr',
    'dojo/html',
    'dojo/query',       //AK added
    'dojo/topic',       //AK added
    'dijit/_WidgetBase',
    'dijit/_TemplatedMixin',
    'dojo/text!./templates/Sublayer.html',
    'dojo/i18n!./../nls/resource'
], function (
    declare,
    lang,
    array,
    on,
    domClass,
    domStyle,
    domAttr,
    html,
    query,  //AK added
    topic,  //AK added
    WidgetBase,
    TemplatedMixin,
    sublayerTemplate,
    i18n
) {
    var _DynamicSublayer = declare([WidgetBase, TemplatedMixin], {
        control: null,
        sublayerInfo: null,
        icons: null,
        // ^args
        templateString: sublayerTemplate,
        i18n: i18n,
        _expandClickHandler: null,
        postCreate: function () {
            this.inherited(arguments);
            var checkNode = this.checkNode;
            domAttr.set(checkNode, 'data-sublayer-id', this.sublayerInfo.id);
            domAttr.set(checkNode, 'data-sublayer-parent-id', this.sublayerInfo.parentLayerId);  //AK added
            domClass.add(checkNode, this.control.layer.id + '-layerControlSublayerCheck');
            if (array.indexOf(this.control.layer.visibleLayers, this.sublayerInfo.id) !== -1) {
                this._setSublayerCheckbox(true, checkNode);
            } else {

                this._setSublayerCheckbox(false, checkNode);
            }
            on(checkNode, 'click', lang.hitch(this, function () {

                if (domAttr.get(checkNode, 'data-checked') === 'checked') {
                    this._setSublayerCheckbox(false, checkNode);
                } else {
                    this._setSublayerCheckbox(true, checkNode);
                }

                //AK start
                //Check if parent need to be CHECKED ON
                var tempnode = checkNode;
                var checkFolder = null;
                do {
                    array.forEach(query('.' + this.control.layer.id + '-layerControlSublayerCheck'), function(i) {
                        if ((domAttr.get(i, 'data-sublayer-id') === domAttr.get(tempnode, 'data-sublayer-parent-id')) && (domAttr.get(tempnode, 'data-checked') === 'checked')) {
                            domAttr.set(i, 'data-checked', 'checked');
                            checkFolder = i;
                        }
                    });
                    if (checkFolder) {
                        this._setSublayerCheckbox(true, checkFolder);
                        if (domAttr.get(checkFolder, 'data-sublayer-parent-id') === "-1") // Root level reached, turn on MapService.
                            topic.publish('layerControl/layerON', {
                                layerId: this.control.layer.id
                            });
                        tempnode = checkFolder; // Move up to folder level..and loop again..
                    }
                    else if (domAttr.get(tempnode, 'data-checked') === 'checked') {
                        topic.publish('layerControl/layerON', {
                            layerId: this.control.layer.id
                        });
                    }

                    //} while (domAttr.get(checkFolder, 'data-sublayer-parent-id') !== "-1");  //This does not work.. checkFolder does not always get set.
                } while (checkFolder && (domAttr.get(tempnode, 'data-sublayer-parent-id') !== "-1"));

                //AK end

                this.control._setVisibleLayers();
                this._checkboxScaleRange();

            }));
            html.set(this.labelNode, this.sublayerInfo.name);
            this._expandClick();
            if (this.sublayerInfo.minScale !== 0 || this.sublayerInfo.maxScale !== 0) {
                this._checkboxScaleRange();
                this.control.layer.getMap().on('zoom-end', lang.hitch(this, '_checkboxScaleRange'));
            }
        },
.
.
.
.
goriliukasbuxton commented 9 years ago

Thank you akakruger for your help, The code turns the map service ON, but group layer doesn't turn on.

goriliukasbuxton commented 9 years ago

Sorry, got it to work, Thank you very much.