Source: widgets/SpwAdvancedIdentify.js

Retour à la documentation
/**
 * @class spw.widgets.SpwAdvancedIdentify
 */
define(["dojo/_base/declare", "spw/api/SpwBaseTemplatedWidget", "dojo/dom-construct", "dojo/_base/array", "dojo/_base/lang",
        "dojo/DeferredList", "esri/tasks/IdentifyTask", "esri/tasks/IdentifyParameters", "esri/tasks/BufferParameters", "esri/tasks/GeometryService",
        "dijit/layout/ContentPane", "dijit/layout/TabContainer", "dijit/registry", "dijit/form/NumberSpinner",
        "spw/api/CollapserItem", "dojo/on", "dojo/mouse", "spw/api/Utils", "dojo/i18n!./nls/SpwAdvancedIdentify",
        "spw/api/MapServiceFactory", "dojo/dom-style", "dojo/dom", "esri/graphic", "esri/toolbars/draw", "esri/geometry/Point", "esri/geometry/Polyline", "esri/geometry/Polygon",
        "esri/symbols/SimpleLineSymbol", "esri/symbols/SimpleMarkerSymbol", "esri/symbols/SimpleFillSymbol", "dojo/_base/Color", "spw/api/ConfigLoader",
        "dojo/text!./templates/SpwAdvancedIdentify.html", "esri/layers/GraphicsLayer", "spw/api/MessageManager", "dojo/touch", "esri/request", "dojo/query",
        "spw/api/Printer", "dojo/Deferred", "dojo/promise/all", "esri/geometry/Extent", "dojo/_base/config",

        "dijit/form/ToggleButton", "dijit/form/Button", "dijit/form/RadioButton", "dijit/form/CheckBox", "dijit/TitlePane",
        "dijit/CheckedMenuItem"],
    function (declare, SpwBaseTemplatedWidget, domConstruct, array, lang,
              DeferredList, IdentifyTask, IdentifyParameters, BufferParameters, GeometryService,
              ContentPane, TabContainer, registry, NumberSpinner,
              CollapserItem, on, mouse, Utils, labels, MapServiceFactory, domStyle, Dom,
              Graphic, Draw, Point, Polyline, Polygon, SimpleLineSymbol, SimpleMarkerSymbol,
              SimpleFillSymbol, Color, ConfigLoader, template, GraphicsLayer, MessageManager, touch, request, query,
              Printer, Deferred, all, Extent, dojoConfig) {

        return declare("spw.widgets.SpwAdvancedIdentify", [SpwBaseTemplatedWidget], /** @lends spw.widgets.SpwAdvancedIdentify.prototype */{

            templateString: template,
            iconClass: "advancedIdentifyIcon",
            labels: labels,

            _toolbar: null,
            _currentBt: null,
            _pointGraph: null,
            _ligneGraph: null,
            _polygoneGraph: null,
            _cercleGraph: null,
            _mouseDragHandler: null,
            _drawBegan: false,
            _identifyTaskQueue: null,
            _srcTreeCollapsed: "",
            _srcTreeExpanded: "",
            _nbPendingIdentify: 0,

            _mapServiceAddedHandler: null,
            _mapServiceRemovedHandler: null,
            _mapServiceVisibilityChangedHandler: null,
            _mapServiceLoadedHandler: null,

            _pointGraph: null,
            _ligneGraph: null,
            _polygoneGraph: null,
            _cercleGraph: null,

            reportParams: {
                "reportTitle": "Rapport dans l'identification",
                "url": dojoConfig.geoviewerApiUrl + "/templates/JasperTemplate.jrxml",
                "jasperServerUrl" : dojoConfig.geoviewerApiUrl + "/Report"
            },

            identifyRunning: false,
            _identifyGraphics: null,
            _currentGraph: null,

            _services: null,
            _identifyResultWidget: null,

            _drawLayer: null,
            tabItems: null,
            geometryService: null,

            FETCH_ALL_CATALOG: "ALL_CATALOG",
            FETCH_ALL_TOC: "ALL_TOC",
            FETCH_ONLY_SELECTED: "ONLY_SELECTED",
            FETCH_ONLY_ADDITIONNAL: "ONLY_ADDITIONNAL",

            /* START widget config */
            fetchMode: null,
            displayServiceName: null,
            specificBuffer: null,
            widgets: null,
            geometryServiceUrl: null,
            additionnalServices: null,

            hasReport: false,
            reportWithLegend: false,
            reportUrl: '//geoservices.test.wallonie.be/geoviewer/Report',
            templateInfo: {
                url: 'reportAdvancedIdentify.jrxml',
                imageWidth: 555 * 1.4,
                imageHeight: 732 * 1.4,
                data: {
                    logoWallon: dojoConfig.geoviewerApiUrl + '/images/templates/logoWallon.png',
                    header1: 'Identification avancée',
                    reportTitle: ''
                }
            },
            /* END widget config */

            _getReportUrlAttr: function() {
                if (this.useCors !== true) {
                    if (/^(http|https):\/\//.test(this.reportUrl) && this.spwViewer.get('proxyPageUrl')) {
                        if (this.reportUrl.indexOf(this.spwViewer.get('proxyPageUrl')) < 0) {
                            return this.spwViewer.get('proxyPageUrl') + '?' + this.reportUrl;
                        }
                    }
                }

                return this.reportUrl;
            },

            /**
             * @constructs
             * @param config
             */
            constructor: function (config) {

                this._identifyGraphics = [];
                this.config = config;
                this.tabItems = new Array();
                this.fetchMode = this.checkAndGetFetchMode(config != null ? config.fetchMode : "");

                this._services = [];
            },

            postMixInProperties: function () {
                this.inherited(arguments);

                this.loadAdditionnalMapServices();

                this.loadMapServicesFromCatalog();

                this.loadResultWidget();
            },

            loadAdditionnalMapServices: function () {
                if (this.additionnalServices != null) {
                    this._additionnalServices = [];
                    array.forEach(this.additionnalServices, lang.hitch(this, function (service) {
                        lang.mixin(service, {
                            type: "AGS_DYNAMIC",
                            mapServicelLoaded: false,
                            spwViewer: this.spwViewer,
                            spwMap: this.spwViewer.get('spwMap')
                        });
                        var mapService = MapServiceFactory.createService(service);
                        on(mapService, "MapServiceLoaded", lang.hitch(this, this.serviceLoaded));
                        this._additionnalServices.push(mapService);
                    }));
                }
            },

            loadMapServicesFromCatalog: function () {
                if (this.fetchMode == this.FETCH_ALL_CATALOG) {
                    var catalogConfig = ConfigLoader.getInstance().get("catalog");

                    array.forEach(catalogConfig, lang.hitch(this, function (serviceGroup, idx) {
                        if (serviceGroup.mapServices && serviceGroup.mapServices.length > 0) {
                            array.forEach(serviceGroup.mapServices, lang.hitch(this, function (service) {
                                lang.mixin(service, {mapServicelLoaded: false});
                                var mapService = MapServiceFactory.createService(service);
                                on(mapService, "MapServiceLoaded", lang.hitch(this, this.serviceLoaded));
                                this._services.push(mapService);
                            }));
                        }
                    }));
                }
            },

            loadResultWidget: function () {
                array.forEach(this.widgets, lang.hitch(this, function (widget) {
                    //if(widget.className == "spw/widgets/SpwIdentifyResult"){
                    require([widget.className], lang.hitch(this, function (widgetClass) {
                        lang.mixin(widget.config, {spwViewer: this.spwViewer, _spwAdvancedIdentify: this});
                        this._identifyResultWidget = new widgetClass(widget.config);
                    }));
                    //}
                }));
            },

            saveGeometry: function(geometry){
                this.currentGeometry = geometry;
            },

            getIdentifyDataForReport: function(evt) {
                var services = this.spwViewer.get('spwMap').getMapServices({ isBaseMap: false, visible: true }), layerPanes = {};
                var promises = [];
                var reportPromises = [];

                array.forEach(services, lang.hitch(this, function(service) {
                    var def = new Deferred();
                    reportPromises.push(def);
                    promises.push(
                        service.identify(lang.mixin(evt, {
                            ignoreFields: this.ignoreFields,
                            tolerance: 10
                        }), lang.hitch(this, function(identifyResults, service, data){
                            if(this.globalIdentifyResults == null){
                                this.globalIdentifyResults = [];
                            }
                            if(this.newIdentifyResultClick){
                                this.globalIdentifyResults = [];
                                this.newIdentifyResultClick = false;
                            }
                            this.globalIdentifyResults.push({service: service, results: identifyResults, data: data});
                            def.resolve([0]);
                        }))
                    );
                }));
                return reportPromises;
            },

            downloadReport: function() {
                var localizationReportDataParams = {
                    geolocalisationApiUrl: this.geolocalisationApiUrl,
                    geolocalisationSRI : this.geolocalisationSRI,
                    altitudeServiceUrl : this.altitudeServiceUrl,
                    mnsServiceUrl : this.mnsServiceUrl,
                    cadmapApiUrl : this.cadmapApiUrl,
                    cadmapSRID : this.cadmapSRID,
                    maxSquareAreaForCadastralReport: this.maxSquareAreaForCadastralReport,
                    identificationType: this.currentGeometry.geometry ? 'polygon':'point'
                };
                this.reportWithLegend = this.reportWithLegend != null ? this.reportWithLegend : true;
                MessageManager.getInstance().displayModalMessage("Interrogation des données thématiques.<br>Cela peut prendre quelques secondes…");
                Utils.getIdentifyDataForReport(this.currentGeometry, this.spwViewer).then(lang.hitch(this, function(identifyResults){
                    MessageManager.getInstance().hideModalMessage();
                    Utils.createReport(this.currentGeometry,localizationReportDataParams, this.reportParams, identifyResults, this.spwViewer, this.reportWithLegend);
                }));
            },

            buildRapportResults: function() {
                var pushedServiceName = [];
                var pushedLayerName = [];
                this._currentReportResults = [];
                if(this.globalIdentifyResults){
                    this.globalIdentifyResults.forEach(lang.hitch(this, function(data){
                        if(pushedServiceName.indexOf(data.service.label) == -1){
                            this._currentReportResults.push({level: -1, label: data.service.label, value: ""});
                            pushedServiceName.push(data.service.label);
                        }
                        if(pushedLayerName.indexOf(data.layerName) == -1){
                            this._currentReportResults.push({level: -2, label: data.layerName, value: ""});
                            pushedLayerName.push(data.layerName);
                        }
                        for(var key in data.feature.attributes){
                            var v = data.feature.attributes[key];
                            this._currentReportResults.push({level: -3, label: key, value: v});
                        }
                    }))
                }
            },

            getTemplate: function(extent, results) {
                var template = this.templateInfo;
                this.repositionWidgets(template);

                this._currentReportResults = results;

                if (template["default"] === true) {
                    this.selectedTemplate = "defaultFileName:" + template.url;

                    //this.destroyPreviewZone();
                    this.printer.getImage(this.spwViewer.get('spwMap').domNode, template.imageWidth, template.imageHeight, true, extent, lang.hitch(this, this.createReport));
                }
                else {
                    request({
                        url: template.url,
                        handleAs: 'text'
                    }).then(
                        lang.hitch(this, function(response) {
                            this.selectedTemplate = lang.mixin(template, {
                                rawTemplate: response
                            });

                            //this.destroyPreviewZone();
                            this.printer.getImage(this.spwViewer.get('spwMap').domNode, template.imageWidth, template.imageHeight, true, extent, lang.hitch(this, this.createReport));

                        }), lang.hitch(this, function(error) {
                            //dans ce cas, url contient la valeur par défaut qui correspond au fichier template par défaut sur le serveur
                            this.selectedTemplate = "defaultFileName:" + template.url;
                            console.log("Template d'impression non trouvé, utilisation du template serveur par défaut : " + template.url);

                            //this.destroyPreviewZone();
                            this.printer.getImage(this.spwViewer.get('spwMap').domNode, template.imageWidth, template.imageHeight, true, extent, lang.hitch(this, this.createReport));
                        }));
                }
            },

            createReport: function(canvas){
                // this.createPreviewZone();

                var img = canvas.toDataURL();
                img = img.substring(img.indexOf(",") + 1);

                var Data = {
                    Data: []
                };

                var Properties = {};

                var promise = new Deferred();

                if(this.reportWithLegend) {
                    var mapServices = this.spwViewer.get('spwMap').getMapServices({
                        isBaseMap: false,
                        visible: true
                    });

                    var recurseLayers = function(layer, level){
                        if(layer.subLayers.length > 0){
                            var l = [];
                            array.forEach(layer.subLayers, function(subLayer){
                                l = l.concat(recurseLayers(subLayer, level + 1));
                            });
                            return l;
                        } else {
                            var legs = [{level:level, label:layer.get('name'),symbol:""}];

                            array.forEach(layer.get('legends'), function(leg){
                                legs.push({
                                    level:level+1,
                                    label:(leg.label ? leg.label : layer.get('name')),
                                    symbol:leg.imageData
                                });
                            });

                            return legs;
                        }
                    };

                    var legPromises = array.map(mapServices, lang.hitch(this, function(mapService){
                        var p = new Deferred();

                        Data.Data.push({
                            level: 0,
                            label: mapService.get('label'),
                            symbol: ""
                        });

                        var loopThroughLayers = function() {
                            array.forEach(mapService.get('mapServiceLayers'), function(subLayer){
                                if(!subLayer.parentLayer) {
                                    Data.Data = Data.Data.concat(recurseLayers(subLayer, 1));
                                }
                            });
                            p.resolve();
                        };

                        if (!mapService.get('legendLoaded')) {
                            this.own(on.once(mapService, mapService.events.MapServiceLegendLoaded, lang.hitch(this, loopThroughLayers)));
                            mapService.loadLegend();
                        }
                        else {
                            loopThroughLayers();
                        }

                        return p;
                    }));

                    all(legPromises).then(lang.hitch(this, function() {
                        promise.resolve();
                    }));
                }
                else {
                    promise.resolve();
                }

                promise.then(lang.hitch(this, function() {
                    var promises = [];

                    for (var key in this.reportParams) {
                        var templateData = this.selectedTemplate.data || {};

                        if (this.reportParams.hasOwnProperty(key)) {
                            var p = new Deferred();
                            promises.push(p);

                            var value = templateData[key] || this.reportParams[key];

                            if ((/\.(gif|jpg|jpeg|tiff|png)$/i).test(value)) {
                                var splitted = value.split('.');
                                var ext = splitted[splitted.length - 1];

                                (function(tmp, k) {
                                    Utils.imgToBase64(value, ext, function(image) {
                                        Properties[k] = image.substring(image.indexOf(",") + 1);
                                        tmp.resolve();
                                    });
                                })(p, key);
                            }
                            else {
                                Properties[key] = value;
                                p.resolve();
                            }
                        }
                    }

                    all(promises).then(lang.hitch(this, function() {
                        this.sendReport(this.get('reportUrl'), this.selectedTemplate.rawTemplate ? this.selectedTemplate.rawTemplate : this.selectedTemplate,
                            img, Data, Properties);
                    }));

                    this.resetWidgets();
                    this.resetNodes();
                }));

            },

            sendReport: function(url, template, mapImage, data, properties) {

                if (this._currentReportResults && this._currentReportResults.length > 0) {
                    data.Data = data.Data.concat(this._currentReportResults);
                }

                this.Data.value = JSON.stringify(data);
                this.Properties.value = JSON.stringify(properties);
                this.FileName.value = "rapport-" + new Date().toLocaleDateString().replace(/\//gim,'-').replace(/ /gim,'-');
                this.Template.value = encodeURIComponent(template);
                this.MapImage.value = mapImage;

                this.formDownload.action = url;

                this.formDownload.submit();

                // iframe._currentDfd = null;
                // iframe(url, {
                //     method: 'POST',
                //     form: this.formDownload
                // });
                //this.formDownload.submit();

                // this.previewZone.show();
            },

            resetWidgets: function() {
                array.forEach(this.ws, lang.hitch(this, function(w) {
                    w.hideOnPrint && domStyle.set(w.domNode, 'display', '');

                    if (w.mapPosition) {
                        domStyle.set(w.domNode, w.mapPosition);
                    }
                }));
            },

            resetNodes: function() {
                array.forEach(this.nodesToReposition, lang.hitch(this, function(nodeToReposition) {
                    var node = query(nodeToReposition)[0];

                    if (node && this.nodesOriginalPosition[nodeToReposition]) {
                        domStyle.set(node, this.nodesOriginalPosition[nodeToReposition]);
                    }
                }));
            },

            repositionWidgets: function(template) {
                var spwMap = this.spwViewer.get('spwMap');

                var overflowW = (template.imageWidth - spwMap.getWidth()) / 2;
                var overflowH = (template.imageHeight - spwMap.getHeight()) / 2;

                array.forEach(this.ws, lang.hitch(this, function(w) {
                    w.hideOnPrint && domStyle.set(w.domNode, 'display', 'none');

                    var mapPosition = w.mapPosition;

                    if (mapPosition) {
                        var top = parseInt(mapPosition.top);
                        var bottom = parseInt(mapPosition.bottom);
                        var right = parseInt(mapPosition.right);
                        var left = parseInt(mapPosition.left);

                        var style = {
                            top: isNaN(top) ? null : top + 'px',
                            left: isNaN(left) ? null : left + 'px',
                            right: isNaN(right) ? null : right + 'px',
                            bottom: isNaN(bottom) ? null : bottom + 'px'
                        };

                        if (overflowH < 0) {
                            if (!isNaN(bottom)) {
                                style.bottom = (bottom - overflowH) + 'px';
                            }
                            else if (!isNaN(top)) {
                                style.top = (top - overflowH) + 'px';
                            }
                        }

                        if (overflowW < 0) {
                            if (!isNaN(right)) {
                                style.right = (right - overflowW) + 'px';
                            }
                            else if (!isNaN(left)) {
                                style.left = (left - overflowW) + 'px';
                            }
                        }

                        domStyle.set(w.domNode, style);
                    }
                }));

                this.nodesOriginalPosition = {};

                array.forEach(this.nodesToReposition, lang.hitch(this, function(nodeToReposition) {
                    var node = query(nodeToReposition)[0];

                    if (node) {
                        var top = parseInt(domStyle.get(node, 'top'));
                        var bottom = parseInt(domStyle.get(node, 'bottom'));
                        var right = parseInt(domStyle.get(node, 'right'));
                        var left = parseInt(domStyle.get(node, 'left'));

                        var style = {
                            top: isNaN(top) ? null : top + 'px',
                            left: isNaN(left) ? null : left + 'px',
                            right: isNaN(right) ? null : right + 'px',
                            bottom: isNaN(bottom) ? null : bottom + 'px'
                        };

                        if (style.top && style.bottom) {
                            delete style.top;
                        }

                        if (style.left && style.right) {
                            delete style.left;
                        }

                        this.nodesOriginalPosition[nodeToReposition] = lang.clone(style);

                        if (overflowH < 0) {
                            if (!isNaN(bottom)) {
                                style.bottom = (bottom - overflowH) + 'px';
                            }
                            else if (!isNaN(top)) {
                                style.top = (top - overflowH) + 'px';
                            }
                        }

                        if (overflowW < 0) {
                            if (!isNaN(right)) {
                                style.right = (right - overflowW) + 'px';
                                delete style.left;
                            }
                            else if (!isNaN(left)) {
                                style.left = (left - overflowW) + 'px';
                            }
                        }

                        domStyle.set(node, style);
                    }
                }));
            },

            checkAndGetFetchMode: function (value) {
                if (value == this.FETCH_ALL_CATALOG || value == this.FETCH_ALL_TOC || value == this.FETCH_ONLY_SELECTED || value == this.FETCH_ONLY_ADDITIONNAL) {
                    return value;
                } else {
                    return this.FETCH_ONLY_SELECTED;
                }
            },

            serviceLoaded: function (service) {
                if (this._services) {
                    if (this._services.contains(service)) {
                        service.mapServicelLoaded = true;
                    }

                    var allLoaded = true;
                    array.forEach(this._services, function (s) {
                        if (!s.mapServicelLoaded) {
                            allLoaded = false;
                        }
                    });
                    if (allLoaded) {
                        this.updateLayersList();
                        this.updateBufferMode();
                    }

                    this.updateLayersList();
                    this.updateBufferMode();
                }
            },

            postCreate: function () {

                this._drawLayer = new GraphicsLayer();
                this._drawLayer.spatialReference = this.spwViewer.get('spatialReference');

                this._srcTreeCollapsed = this.get('imagesPath') + "treeCollapsed.png";
                this._srcTreeExpanded = this.get('imagesPath') + "treeExpanded.png";
                this._toolbar = new Draw(this.spwViewer.get('spwMap').get('esriMap'), {showTooltips: true});

                this.own(
                    on(this.spwViewer.get('spwMap'), this.spwViewer.get('spwMap').events.MapDestroyed, lang.hitch(this, function () {
                        this._toolbar = null;
                        this.disableCurrentBt();
                    })),
                    on(this.spwViewer.get('spwMap'), this.spwViewer.get('spwMap').events.MapCreated, lang.hitch(this, function (map) {
                        this.disableCurrentBt();
                        this._toolbar = new Draw(map, {showTooltips: true});
                        on(this._toolbar, "draw-end", lang.hitch(this, this.onDrawEnded));
                    }))
                );

                if (this.get('geometryServiceUrl')) {
                    this.geometryService = new GeometryService(this.get('geometryServiceUrl'));
                }
                else {
                    this.geometryService = this.spwViewer.get('geometryService');
                }

                this.connect();
                this.style();
                this.graphics();

                this.inherited(arguments);

                if (this.hasReport) {
                    domStyle.set(this.btReport.domNode, 'display', '');

                    on(this.btReport, 'click', lang.hitch(this, function() {
                        this.identify(this._currentGraph.geometry, true);
                    }));
                }
            },

            onActivate: function () {
                this.inherited(arguments);

                this.spwViewer.get('spwMap').get('esriMap').addLayer(this._drawLayer);

                this.initValues();

                this.addEventListeners();
            },

            addEventListeners: function () {
                this._mapServiceAddedHandler = on(this.spwViewer.get('spwMap'), "MapServiceAdded", lang.hitch(this, this.updateLayersList));
                this._mapServiceRemovedHandler = on(this.spwViewer.get('spwMap'), "MapServiceRemoved", lang.hitch(this, this.updateLayersList));
                this._mapServiceVisibilityChangedHandler = on(this.spwViewer.get('spwMap'), "MapServiceVisibilityChanged", lang.hitch(this, this.updateLayersList));
                this._mapServiceLoadedHandler = on(this.spwViewer.get('spwMap'), "MapServiceLoaded", lang.hitch(this, this.updateLayersList));
            },

            onDeactivate: function () {
                this.inherited(arguments);

                this.disableCurrentBt();

                if (this._mapServiceAddedHandler)
                    this._mapServiceAddedHandler.remove();

                if (this._mapServiceRemovedHandler)
                    this._mapServiceRemovedHandler.remove();

                if (this._mapServiceVisibilityChangedHandler)
                    this._mapServiceVisibilityChangedHandler.remove();

                if (this._mapServiceLoadedHandler)
                    this._mapServiceLoadedHandler.remove();

                if (this._identifyResultWidget) {
                    if (this._identifyResultWidget.get('activated')) {
                        this._identifyResultWidget.onDeactivate();
                    }
                }

                this.spwViewer.get('spwMap').get('esriMap').removeLayer(this._drawLayer);
                this.hideLoading();
            },

            style: function () {

                domStyle.set(this.btPoint, "width", "60px");
                domStyle.set(this.btLigne, "width", "60px");
                domStyle.set(this.btPolygone, "width", "60px");
                domStyle.set(this.btCercle, "width", "60px");
                domStyle.set(this.btIdentify, "width", "75px");
                domStyle.set(this.btReInit, "width", "75px");
                //domStyle.set(this.spLayersList.domNode,"height","92px");
                //domStyle.set(this.spLayersList.domNode,"width","92%");
                //domStyle.set(this.spLayersList.domNode,"overflow","auto");
                //domStyle.set(this.spLayersList.domNode,"position","relative");

                if (typeof this.specificBuffer == "undefined" || this.specificBuffer == false) {
                    this.radioGlobalBuffer.set("checked", true);
                    domStyle.set(this.radioGlobalBuffer.domNode, "display", "none");
                    domStyle.set(this.trSpecificBuffer.domNode, "display", "none");
                }
            },

            graphics: function () {

                var spatRef = this.spwViewer.get("spatialReference");
                this._pointGraph = new Graphic(new Point(spatRef), new SimpleMarkerSymbol(SimpleMarkerSymbol.STYLE_DIAMOND, 15, new SimpleLineSymbol(SimpleLineSymbol.STYLE_SOLID, new Color([0, 0, 255]), 1), new Color([0, 0, 255, 0.5])));
                this._ligneGraph = new Graphic(new Polyline(spatRef), new SimpleLineSymbol(SimpleLineSymbol.STYLE_SOLID, new Color([0, 0, 255]), 1));
                this._polygoneGraph = new Graphic(new Polygon(spatRef), new SimpleFillSymbol(SimpleFillSymbol.STYLE_SOLID, new SimpleLineSymbol(SimpleLineSymbol.STYLE_SOLID, new Color([0, 0, 255]), 2), new Color([0, 0, 255, 0.25])));
                this._cercleGraph = new Graphic(new Polygon(spatRef), new SimpleFillSymbol(SimpleFillSymbol.STYLE_SOLID, new SimpleLineSymbol(SimpleLineSymbol.STYLE_SOLID, new Color([0, 0, 255]), 2), new Color([0, 0, 255, 0.25])));
                this._resultGraph = new Graphic(new Polygon(spatRef), new SimpleFillSymbol(SimpleFillSymbol.STYLE_SOLID, new SimpleLineSymbol(SimpleLineSymbol.STYLE_SOLID, new Color([0, 0, 255]), 2), new Color([0, 0, 255, 0.25])));

                this._drawLayer.add(this._pointGraph);
                this._drawLayer.add(this._ligneGraph);
                this._drawLayer.add(this._polygoneGraph);
                this._drawLayer.add(this._cercleGraph);
                this._drawLayer.add(this._resultGraph);

                this._pointGraph.hide();
                this._ligneGraph.hide();
                this._polygoneGraph.hide();
                this._cercleGraph.hide();
                this._resultGraph.hide();
            },

            connect: function () {
                on(this.btPoint, 'change', lang.hitch(this, this.onClickBtPoint));
                on(this.btLigne, 'change', lang.hitch(this, this.onClickBtLigne));
                on(this.btPolygone, 'change', lang.hitch(this, this.onClickBtPolygone));
                on(this.btCercle, 'change', lang.hitch(this, this.onClickBtCercle));
                on(this.btIdentify, touch.press, lang.hitch(this, this.onClickBtIdentify));
                on(this.btReInit, touch.press, lang.hitch(this, this.onClickBtReInit));
                on(this.radioGlobalBuffer, "change", lang.hitch(this, this.updateBufferMode));
                on(this.cbUseBuffer, 'change', lang.hitch(this, this.updateBufferMode));
                on(this._toolbar, "draw-end", lang.hitch(this, this.onDrawEnded));
            },

            initValues: function () {
                this.btIdentify.set("disabled", true);
                var buffer = this.getInitBuffer();
                this.nsGlobalBuffer.set("value", buffer);
                this.radioGlobalBuffer.set("checked", true);
                this.radioSpecificBuffer.set("checked", false);
                this.cbUseBuffer.set("checked", true);

                this.updateLayersList();
            },

            updateBufferMode: function () {
                var i = 0;
                var tabOpts = this.tabItems;
                if (this.cbUseBuffer.get("checked")) {
                    this.nsGlobalBuffer.set("disabled", false);
                    this.radioGlobalBuffer.set("disabled", false);
                    this.radioSpecificBuffer.set("disabled", false);
                    while (i < tabOpts.length) {
                        var spin = tabOpts[i].nsSpecBuffer;
                        if (typeof spin != "undefined") {
                            tabOpts[i].nsSpecBuffer.set("disabled", false);
                        }
                        i++;
                    }
                    i = 0;
                    if (this.radioGlobalBuffer.get("checked")) {
                        domStyle.set(this.nsGlobalBuffer.domNode, "display", "");

                        while (i < tabOpts.length) {
                            var spin = tabOpts[i].nsSpecBuffer;
                            if (typeof spin != "undefined") {
                                domStyle.set(tabOpts[i].nsSpecBuffer.domNode, "display", "none");
                            }
                            i++;
                        }
                    } else {
                        domStyle.set(this.nsGlobalBuffer, "display", "none");
                        while (i < tabOpts.length) {
                            var spin = tabOpts[i].nsSpecBuffer;
                            if (typeof spin != "undefined") {
                                domStyle.set(tabOpts[i].nsSpecBuffer.domNode, "display", "");
                            }
                            i++;
                        }
                    }
                } else {
                    this.nsGlobalBuffer.set("disabled", true);
                    this.radioGlobalBuffer.set("disabled", true);
                    this.radioSpecificBuffer.set("disabled", true);
                    while (i < tabOpts.length) {
                        var spin = tabOpts[i].nsSpecBuffer;
                        if (typeof spin != "undefined") {
                            tabOpts[i].nsSpecBuffer.set("disabled", true);
                        }
                        i++;
                    }
                    i = 0;
                }
            },

            getInitBuffer: function () {
                var config = this.config;
                var buffer = 0;
                if (typeof config != "undefined") {
                    if (typeof config.initBuffer != "undefined" && config.initBuffer > 0) {
                        buffer = config.initBuffer;
                    }
                }
                return buffer;
            },

            updateCollapser: function (opt) {
                if (opt.collapsed == true) {
                    opt.collapsed = false;
                    domStyle.set(Dom.byId(opt.childsId), "display", "");
                    Dom.byId(opt.expImId).src = this._srcTreeExpanded;
                }
                else {
                    opt.collapsed = true;
                    domStyle.set(Dom.byId(opt.childsId), "display", "none");
                    Dom.byId(opt.expImId).src = this._srcTreeCollapsed;
                }
            },

            onClickBtPoint: function () {
                if (this._disableEvent) {
                    this._disableEvent = false;
                    return;
                }

                if (this.btPoint.get("checked")) {
                    this.disableCurrentBt();
                    this._toolbar.activate(Draw.POINT);
                    this._toolbar._tooltip.innerHTML = this.labels.clickToFixPoint;
                    this._currentBt = this.btPoint;
                    this._currentGraph = this._pointGraph;
                }
                else {
                    this.disableCurrentBt();
                }
            },

            onClickBtLigne: function () {
                if (this._disableEvent) {
                    this._disableEvent = false;
                    return;
                }

                if (this.btLigne.get("checked")) {
                    this.disableCurrentBt();
                    this._toolbar.activate(Draw.POLYLINE);
                    this._currentBt = this.btLigne;
                    this._currentGraph = this._ligneGraph;
                }
                else {
                    this.disableCurrentBt();
                }
            },

            onClickBtPolygone: function () {
                if (this._disableEvent) {
                    this._disableEvent = false;
                    return;
                }

                if (this.btPolygone.get("checked")) {
                    this.disableCurrentBt();
                    this._toolbar.activate(Draw.POLYGON);
                    this._currentBt = this.btPolygone;
                    this._currentGraph = this._polygoneGraph;
                }
                else {
                    this.disableCurrentBt();
                }
            },

            onClickBtCercle: function () {
                if (this._disableEvent) {
                    this._disableEvent = false;
                    return;
                }

                if (this.btCercle.get("checked")) {
                    this.disableCurrentBt();
                    this._toolbar.activate(Draw.FREEHAND_POLYLINE);
                    this._currentBt = this.btCercle;
                    this._currentGraph = this._cercleGraph;
                    this.own(
                        this._mouseDragHandler = on(this.spwViewer.get('spwMap').get('esriMap'), "MouseDrag", lang.hitch(this, this.onMouseDragCercle))
                    );
                    this._toolbar.lineSymbol.color.a = 0;
                }
                else {
                    this.disableCurrentBt();
                }
            },

            onClickBtReInit: function () {
                this.disableCurrentBt();
                this.initValues();
            },

            onMouseDragCercle: function (evt) {
                if (!this._drawBegan) {
                    this._drawBegan = true;
                    this._toolbar._firstPoint = evt.mapPoint;
                }
                else {
                    this._toolbar._currentPoint = evt.mapPoint;
                    var geom = new Object();
                    geom.paths = new Array();
                    geom.paths[0] = new Array();
                    geom.paths[0].push([this._toolbar._firstPoint.x, this._toolbar._firstPoint.y]);
                    geom.paths[0].push([this._toolbar._currentPoint.x, this._toolbar._currentPoint.y]);
                    geom.spatialReference = this.spwViewer.get("spatialReference");
                    geom = this.buildCircle(geom);
                    this._currentGraph.setGeometry(geom);
                    this._currentGraph.show();
                }
            },

            disableCurrentBt: function () {
                if (this._currentBt != null) {
                    this._disableEvent = true;
                    this._currentBt.set("checked", false);
                }
                if (this._currentGraph != null) {
                    this._currentGraph.hide();
                }
                if (this._mouseDragHandler != null) {
                    this._mouseDragHandler.remove();
                }
                this._currentBt = null;
                this._currentGraph = null;

                if (this._toolbar) {
                    this._toolbar.lineSymbol.color.a = 1;
                    this._toolbar.deactivate();
                }

                if (this.btIdentify) {
                    this.btIdentify.set("disabled", true);
                }
            },

            onDrawEnded: function (geom) {
                var g = geom.geometry ? geom.geometry : geom;
                //permet de ne pas retracer un freehandpolygon lorsque l'on dessine un cercle
                if (this._currentBt != null) {
                    this._disableEvent = true;
                    this._currentBt.set("checked", false);
                    this._currentBt = null;
                }

                this._toolbar.deactivate();
                if (this._currentGraph.geometry.type == g.type) {
                    this.showGeom(g);
                }
                this.btIdentify.set("disabled", false);
                this._drawBegan = false;
                if (this._mouseDragHandler != null) {
                    this._mouseDragHandler.remove();
                }
            },

            showGeom: function (geom) {

                this._currentGraph.setGeometry(geom);
                this._currentGraph.show();
            },

            onClickBtIdentify: function () {
                this.globalIdentifyResults = [];
                if (this._identifyResultWidget) {
                    this._identifyResultWidget.clearResults();
                }
                this.saveGeometry(this._currentGraph);
                this.identify(this._currentGraph.geometry);
            },

            setResultGeometry: function (geom) {

                this.geometryService.union(
                    geom,
                    lang.hitch(this, function (unionedGeom) {
                        this.disableCurrentBt();
                        if (unionedGeom.type.indexOf("point") != -1) {
                            this._currentGraph = this._pointGraph;
                        }
                        else {
                            this._currentGraph = this._resultGraph;
                        }
                        this._currentGraph.setGeometry(unionedGeom);
                        this.onDrawEnded(unionedGeom);
                    }),
                    lang.hitch(this, function (error) {
                        MessageManager.getInstance().notifyError("Erreur lors de l'union : " + error.toString());
                    }));
            },

            identify: function (geom, report) {
                this._generateReport = (report === true);

                if (this._identifyResultWidget && !this._generateReport) {
                    if (!this._identifyResultWidget.get('activated')) {
                        this._identifyResultWidget.onActivate();
                    }
                }
                //var geom = this._currentGraph.geometry;
                if (this.cbUseBuffer.get("checked")) {
                    if (this.isGlobalBufferMode()) {
                        this.bufferGlobal(geom, this.nsGlobalBuffer.value);
                    }
                    else {
                        this.bufferSpecific(geom);
                    }
                } else {
                    this.globalIdentify(geom);
                }
            },

            bufferGlobal: function (geom, buff) {
                if (buff != 0) {
                    var buffParms = new BufferParameters();
                    buffParms.bufferSpatialReference = this.spwViewer.get("spatialReference");
                    buffParms.geometries = [geom];
                    buffParms.distances = [buff];
                    buffParms.unit = GeometryService.UNIT_METER;
                    this.geometryService.buffer(buffParms, lang.hitch(this, function (geoms) {
                        this.globalIdentify(geoms[0]);
                    }), lang.hitch(this, function (error) {
                        MessageManager.getInstance().notifyError("Erreur lors de la bufferisation : " + error.toString());
                        this.hideLoading();
                        if (this._identifyResultWidget) {
                            this._identifyResultWidget.hideLoadingImage();
                        }
                    }));
                }
                else {
                    this.globalIdentify(geom);
                }
            },

            bufferSpecific: function (geom) {
                this._identifyTaskQueue = new Array();
                var buffParms = new BufferParameters();
                buffParms.bufferSpatialReference = this.spwViewer.get("spatialReference");
                var tabBuff = new Array();
                var opts = this.getSelectedLayers();
                var i = 0;
                while (i < opts.length) {
                    if (opts[i].nsSpecBuffer.value != 0) {
                        tabBuff.push(opts[i].nsSpecBuffer.value);
                    }
                    else {
                        this.specificIdentify(geom, opts[i]);
                    }

                    i++;
                }
                if (tabBuff.length > 0) {
                    buffParms.geometries = [geom];
                    buffParms.distances = tabBuff;
                    buffParms.unit = GeometryService.UNIT_METER;
                    this.geometryService.buffer(buffParms, lang.hitch(this, function (geoms) {
                        var i = 0;
                        var j = 0;
                        while (i < opts.length) {
                            if (opts[i].nsSpecBuffer.value != 0) {
                                this.specificIdentify(geoms[j], opts[i]);
                                j++;
                            }
                            i++;
                        }
                        this._reportResults = [];
                        this.executeIdentify();
                    }), lang.hitch(this, function (error) {
                        MessageManager.getInstance().notifyError("Erreur lors de la bufferisation : " + error.toString());
                        this.hideLoading();
                        if (this._identifyResultWidget) {
                            this._identifyResultWidget.hideLoadingImage();
                        }
                    }));
                }
            },

            specificIdentify: function (geom, opt) {

                this._nbPendingIdentify++;
                var mapService = opt.layer.get('mapService');

                var identifyParams = new IdentifyParameters();
                identifyParams.tolerance = 0;
                identifyParams.returnGeometry = true;
                identifyParams.spatialReference = this.spwViewer.get("spatialReference");
                var arr = new Array();
                arr.push(opt.layer.get('serviceId'));
                identifyParams.layerIds = arr;
                identifyParams.layerOption = IdentifyParameters.LAYER_OPTION_ALL;
                identifyParams.width = this.spwViewer.get('spwMap').get('esriMap').width;
                identifyParams.height = this.spwViewer.get('spwMap').get('esriMap').height;
                identifyParams.geometry = geom;

                identifyParams.mapExtent = this.spwViewer.get('spwMap').get('esriMap').extent;
                //Will work only with a ArcGIS Server 10 MapService (ESRI limitation)
                identifyParams.layerDefinitions = opt.layer.get('layerDefinitions');
                var identifyTask = new IdentifyTask(mapService.get('url'));
                this._identifyTaskQueue.push({
                    identifyTask: identifyTask,
                    identifyParams: identifyParams,
                    layers: [opt]
                });
                this._reportResults = [];
                this.executeIdentify();
            },

            globalIdentify: function (geom) {
                var opts = this.getSelectedLayers();
                var mapServices = this.getServicesToIdentify();
                if(mapServices.length > 0) {
                    this._identifyResultWidget.displayLoadingImage();
                    this.showLoading();
                    this._identifyTaskQueue = new Array();

                    //Create identifyTasks for visible map services
                    for (var i = 0; i < mapServices.length; i++) {
                        this.pushIdentifyTaskInQueue(mapServices[i], opts, geom);
                    }

                    //Create identifyTasks for additionnal map services
                    array.forEach(this._services, lang.hitch(this, function (service) {
                        this.pushIdentifyTaskInQueue(service, opts, geom);
                    }));

                    this._reportResults = [];
                    this.executeIdentify();
                } else {
                    MessageManager.getInstance().notifyInfo("Aucune couche thématique à interroger.");
                }

            },

            pushIdentifyTaskInQueue: function (mapService, opts, geom) {
                var identifyParams = new IdentifyParameters();
                identifyParams.tolerance = 0;
                identifyParams.returnGeometry = true;
                identifyParams.spatialReference = this.spwViewer.get("spatialReference");
                var j = 0;
                var arr = new Array();
                var tabLayers = new Array();
                while (j < opts.length) {
                    if (opts[j].layer.get('mapService').get('serviceId') == mapService.get('serviceId')) {
                        arr.push(opts[j].layer.get('layerId'));
                        tabLayers.push(opts[j]);
                    }
                    j++;
                }
                if (arr.length > 0) {

                    this._nbPendingIdentify++;
                    identifyParams.layerIds = arr;
                    identifyParams.layerOption = IdentifyParameters.LAYER_OPTION_ALL;
                    identifyParams.width = this.spwViewer.get('spwMap').get('esriMap').width;
                    identifyParams.height = this.spwViewer.get('spwMap').get('esriMap').height;

                    identifyParams.geometry = geom;

                    identifyParams.mapExtent = this.spwViewer.get('spwMap').get('esriMap').extent;
                    //Will work only with a ArcGIS Server 10 MapService (ESRI limitation)
                    identifyParams.layerDefinitions = mapService.get('layerDefinitions');
                    var identifyTask = new IdentifyTask(mapService.get('url'));
                    tabLayers['SERVICE_LABEL'] = mapService.label;
                    this._identifyTaskQueue.push({
                        identifyTask: identifyTask,
                        identifyParams: identifyParams,
                        layers: tabLayers
                    });
                }
            },

            executeIdentify: function () {
                if(this.globalIdentifyResults == null){
                    this.globalIdentifyResults = [];
                }
                if (this._identifyTaskQueue.length > 0) {
                    var current = this._identifyTaskQueue.pop();
                    current.identifyTask.execute(current.identifyParams,
                        lang.hitch(this, function (results) {
                            if(results && results.length > 0){
                                results.forEach(lang.hitch(this, function(res){
                                    res['service'] = {};
                                    res['service']['label'] = current.layers['SERVICE_LABEL'];
                                    this.globalIdentifyResults.push(res);
                                }))
                            }
                            this.onResultIdentifyReceived(results, current.layers);
                            this._identifyRunning = false;

                            if (!this.executeIdentify()) {

                                if (this._generateReport) {
                                    this.downloadReport(this._reportResults);
                                }
                                else if (this._identifyResultWidget) {
                                    this._identifyResultWidget.hideLoadingImage();
                                }

                                this.hideLoading();
                            }
                        }),
                        lang.hitch(this, function (error) {
                            MessageManager.getInstance().notifyError("Erreur lors de l'identification : " + error.toString());
                            this.hideLoading();
                            if (this._identifyResultWidget) {
                                this._identifyResultWidget.hideLoadingImage();
                            }
                        })
                    );
                    return true;
                }
                return false;
            },

            _reportResults: null,

            onResultIdentifyReceived: function (results, opts) {
                this._nbPendingIdentify--;
                var j = 0;
                this._reportResults.push({
                    level: -1,
                    label: opts['SERVICE_LABEL']
                });
                while (j < opts.length) {
                    var i = 0;
                    var tabResults = new Array();

                    while (i < results.length) {

                        if (opts[j].layer.get('layerId') == results[i].layerId) {
                            results[i].feature.geometry.setSpatialReference(this.spwViewer.get('spatialReference'));
                            tabResults.push(results[i]);
                        }
                        i++;
                    }
                    array.forEach(tabResults, lang.hitch(this, function(tabResult, idx) {
                        if (tabResult == null || tabResult.feature == null || tabResult.feature.attributes == null) {
                            return;
                        }
                        this._reportResults.push({
                            level: -2,
                            label: tabResult.layerName,
                            value: ''
                        });
                        for (var key in tabResult.feature.attributes) {
                            if (tabResult.feature.attributes.hasOwnProperty(key)) {
                                this._reportResults.push({
                                    level: -3,
                                    label: key,
                                    value: tabResult.feature.attributes[key]
                                });
                            }
                        }
                    }));
                    if (!this._generateReport && this._identifyResultWidget && tabResults.length > 0) {
                        this._identifyResultWidget.addResults(tabResults, opts[j].layer);
                    }
                    j++;
                }

            },

            isGlobalBufferMode: function () {
                return this.radioGlobalBuffer.get("checked");
            },

            getSelectedLayers: function () {
                var i = 0;
                var tabOpts = this.tabItems;
                var tabSelectedLayers = new Array();
                while (i < tabOpts.length) {
                    if (tabOpts[i].layer.get('subLayers').length == 0) {
                        if (typeof registry.byId(tabOpts[i].cbId) == "undefined") {
                            tabOpts.splice(i, 1);
                            i--;
                        } else if (registry.byId(tabOpts[i].cbId).get("checked")) {
                            tabSelectedLayers.push(tabOpts[i]);
                        }
                    }

                    i++;
                }
                return tabSelectedLayers;
            },

            getServicesToIdentify: function () {
                if (this.fetchMode == this.FETCH_ALL_CATALOG) {
                    // In this case, all map services are loaded at construction
                    return [];
                } else if (this.fetchMode == this.FETCH_ALL_TOC) {
                    return this.spwViewer.get('spwMap').getMapServices();
                } else if (this.fetchMode == this.FETCH_ONLY_ADDITIONNAL) {
                    return this._additionnalServices;
                }
                return this.spwViewer.get('spwMap').getMapServices({visible: true, isBaseMap: false});
            },

            updateLayersList: function () {

                this.emptyLayerList();
                var mapServices = this.getServicesToIdentify();

                // get the services loaded by the widget
                if (this._services != null && this._services.length > 0) {
                    array.forEach(this._services, function (s) {
                        if (s.mapServicelLoaded) {
                            mapServices.push(s);
                        }
                    });
                }

                var txt = "<table class='advancedIdentifyTable'>";
                var i = 0;
                while (i < mapServices.length) {
                    var mapService = mapServices[i];

                    if (mapService.identifiable === false) {
                        i++;
                        continue;
                    }

                    if (this.config.displayServiceName) {
                        txt += "<tr><td style='font-weight:bold;" + (i > 0 ? "border-top:1px solid grey;padding-top: 5px;" : "") + "'>" + mapService.get('label') + "</td></tr>";
                    }
                    var layers = mapService.getParentMapServiceLayers();
                    var j = 0;

                    while (j < layers.length) {
                        layer = layers[j];

                        if (layer.identifiable === false) {
                            ++j;
                            continue;
                        }

                        if (this.fetchMode != this.FETCH_ONLY_SELECTED || layer.isVisible()) {
                            var item = this.getLayerItem(0, layer);
                            txt += "<tr><td>" + item.txt + "</td></tr>";
                        }
                        j++;
                    }

                    i++;
                }
                txt += "</table>";
                this.spLayersList.set("content", txt);
                this.addSpinners();
                this.addCollapserEvent();
                this.addCheckBoxEvent();

                this.updateBufferMode();
            },

            addSpinners: function () {

                var i = 0;
                var tab = this.tabItems;
                while (i < tab.length) {
                    var item = tab[i];
                    if (item.layer.get('subLayers').length == 0 && (registry.byId(item.spinId) == null || typeof registry.byId(item.spinId) == "undefined" )) {
                        var specificBuffer = new NumberSpinner({
                            value: this.getInitBuffer(),
                            smallDelta: 1,
                            constraints: {min: 0, max: 9999, places: 0, pattern: '####'},
                            id: item.spinId,
                            style: "width:75px;z-index:100;"
                        }, item.spinId);
                        item.nsSpecBuffer = specificBuffer;
                        domStyle.set(specificBuffer.domNode, "display", "none");
                        domStyle.set(specificBuffer.domNode, "right", "0px");
                        //specificBuffer.startup();
                    }
                    i++;
                }

            },
            addCollapserEvent: function () {
                var i = 0;
                var tab = this.tabItems;
                while (i < tab.length) {
                    var item = tab[i];
                    if (item.layer.get('subLayers').length > 0 && Dom.byId(item.expId) != null) {
                        var context = this;
                        Dom.byId(item.expId).item = item;
                        Dom.byId(item.expId).onclick = function () {
                            context.updateCollapser(this.item);
                        };
                    }
                    i++;
                }
            },
            addCheckBoxEvent: function () {
                var i = 0;
                var tab = this.tabItems;
                while (i < tab.length) {
                    var item = tab[i];
                    if (Dom.byId(item.cbId) != null) {
                        Dom.byId(item.cbId).item = item;
                        on(Dom.byId(item.cbId), 'change', lang.hitch(this, this.onClickCheckBoxe));
                    }
                    i++;
                }
            },

            setChildrenCheckBoxes: function (item, checked) {
                var j = 0;
                while (j < item.layer.get('subLayers').length) {
                    var subLayer = item.layer.get('subLayers')[j];
                    var i = 0;
                    var tab = this.tabItems;
                    while (i < tab.length) {
                        var itemBis = tab[i];
                        if (itemBis.layer.get('layerId') == subLayer.get('layerId') && itemBis.layer.get('mapService').get('serviceId') == subLayer.get('mapService').get('serviceId')) {
                            registry.byId(itemBis.cbId).set("checked", checked);
                        }
                        i++;
                    }

                    j++;
                }
            },

            onClickCheckBoxe: function (e) {
                var checked = (e.target || e.srcElement).checked;
                var item = (e.target || e.srcElement).item;
                this.setChildrenCheckBoxes(item, checked);
                j = 0;
                var parent = item.layer.get('parentLayer');
                if (parent != null) {
                    var nbSubLayer = 0;
                    var itemParent;
                    var nbChecked = 0;
                    var nbUnChecked = 0;
                    while (j < item.layer.get('parentLayer').get('subLayers').length) {
                        var subLayer = item.layer.get('parentLayer').get('subLayers')[j];
                        if (this.fetchMode != this.FETCH_ONLY_SELECTED || subLayer.isVisible()) {
                            nbSubLayer++;
                            var i = 0;
                            var tab = this.tabItems;
                            while (i < tab.length) {
                                var itemBis = tab[i];
                                if (itemBis.layer == subLayer) {
                                    if (registry.byId(itemBis.cbId).get("checked")) {
                                        nbChecked++;
                                    } else {
                                        nbUnChecked++;
                                    }
                                } else if (itemBis.layer == parent) {
                                    itemParent = itemBis;
                                }
                                i++;
                            }
                        }
                        j++;
                    }
                    if (nbSubLayer == nbChecked) {
                        this.setChildrenCheckBoxes(itemParent, true);
                        registry.byId(itemParent.cbId).set("checked", true);
                    } else /*if(nbSubLayer==nbUnChecked)*/ {
                        //this.setChildrenCheckBoxes(itemParent, false);
                        registry.byId(itemParent.cbId).set("checked", false);
                    }
                }
            },

            emptyLayerList: function () {
                this.tabItems = new Array();
            },

            getLayerItem: function (niveau, layer) {
                var label = layer.get('displayLabel') || layer.get('name');
                var id = "" + layer.get('mapService').get('serviceId') + layer.get('layerId');
                var expId = "expId" + id;
                var expImId = "expImId" + id;
                var cbId = "cb" + id;
                var spinId = "spin" + id;
                var childsId = "childs" + id;
                var shortLabel = label;
                if (shortLabel.length > 25) {
                    shortLabel = shortLabel.substring(0, 15);
                    shortLabel = shortLabel + "...";
                }
                var txt = "<table style='width:100%;' >" +
                    "<tr title='" + label + "'>" +
                    "<td id='" + expId + "' style='width:" + ((niveau + 1) * 16) + "px;left:" + ((niveau) * 15) + "px;position:relative;'>";
                var display = "cursor:pointer;";
                if (layer.get('subLayers').length == 0) {
                    display = "display:none";
                }
                txt += "<img id='" + expImId + "'src='" + this._srcTreeExpanded + "' style='" + display + "'>";
                txt += "</td>" +
                    "<td style='width:16px;'>" +
                    "<span id='" + cbId + "' dojoType=\"dijit.form.CheckBox\" style=\"cursor:pointer;\" checked></span>" +
                    "</td>" +
                    "<td>" +
                    shortLabel +
                    "</td>" +
                    "<td style='text-align:right;width:80px;'>" +
                    "<div id=" + spinId + "></div>" +
                    "</td>" +
                    "</tr>" +
                    "</table>";

                txt += "<span id=" + childsId + " style=''>";
                var i = 0;
                var subLayers = layer.get('subLayers');
                while (i < subLayers.length) {
                    var subLayer = subLayers[i];
                    if (this.fetchMode != this.FETCH_ONLY_SELECTED || subLayer.isVisible()) {
                        var item = this.getLayerItem(niveau + 1, subLayer);
                        txt += item.txt;
                    }
                    i++;
                }
                txt += "</span>";

                var item = {
                    layer: layer,
                    expId: expId,
                    expImId: expImId,
                    cbId: cbId,
                    spinId: spinId,
                    childsId: childsId,
                    txt: txt
                };
                this.tabItems.push(item);
                return item;

            },

            buildCircle: function (geom) {
                var p1, p2, radius, circle, ring, pts, angle;

                if (geom.paths[0].length < 2) {
                    MessageManager.getInstance().notifyError(this.labels.createCircleError);
                    return null;
                }

                p1 = geom.paths[0][0]; // circle center
                p2 = geom.paths[0][geom.paths[0].length - 1]; // point on the circle
                radius = Math.pow((Math.pow((p2[0] - p1[0]), 2) + Math.pow((p2[1] - p1[1]), 2)), 0.5);
                circle = new esri.geometry.Polygon(this.spwViewer.get("spatialReference"));
                ring = []; // point that make up the circle
                pts = 30; // number of points on the circle
                angle = 360 / pts; // used to compute points on the circle
                for (var i = 1; i <= pts; i++) {
                    // convert angle to raidans
                    var radians = i * angle * Math.PI / 180;
                    // add point to the circle
                    ring.push([p1[0] + radius * Math.cos(radians), p1[1] + radius * Math.sin(radians)]);
                }
                ring.push(ring[0]); // start point needs to == end point
                circle.addRing(ring);
                return circle;
            }
        });
    });