Source: widgets/SpwIdentify.js

Retour à la documentation
/**
 * @class spw.widgets.SpwIdentify
 */
define([
        "dojo/_base/declare","spw/api/SpwBaseTemplatedWidget", "dojo/text!./templates/SpwIdentify.html",
        "dijit/TitlePane", "dojo/_base/lang", "spw/api/ProjectionManager", "esri/tasks/IdentifyTask",
        "esri/tasks/IdentifyParameters", "dojo/dom-construct", "dojo/_base/array", "dojo/on", "dojo/mouse",
        "dojo/dom-style", "esri/geometry/Polygon", "esri/geometry/Point", "esri/graphic", "dojo/aspect",
        "dojo/promise/all", "esri/SpatialReference", "dijit/layout/ContentPane", "dojo/touch", "spw/api/GraphicsMapService",
        "esri/request", "spw/api/GeometryConverter", "spw/api/MapServiceFactory", "dijit/form/Select", "dojo/store/Memory",
        "spw/api/MessageManager", "spw/api/SpwDrawToolbar", "esri/tasks/QueryTask", "esri/tasks/query", "dojo/Deferred",
        "spw/api/GeometryUtils", "spw/api/SpwViewer", "spw/api/Printer", "spw/api/Utils"
    ],
    function(declare, SpwBaseTemplatedWidget, tmpl, TitlePane, lang, ProjectionManager,
             IdentifyTask, IdentifyParameters, domConstruct, array, on, mouse, domStyle,
             Polygon, Point, Graphic, aspect, all, SpatialReference, ContentPane, touch,
             GraphicsMapService, request, GeometryConverter, MapServiceFactory, Select, Memory,
             MessageManager, Draw, QueryTask, Query, Deferred, GeometryUtils, SpwViewer, Printer, Utils) {

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

            informationVisible: ['address', 'coordinates', 'altitude', 'mns', 'cadastre'],
            printWidgetId:'SpwPrintId',

            templateString: tmpl, 

            geolocalisationSRID: 31370,

            canExport: false,

            segmentationApiUrl: "//geoservices.wallonie.be/segmentation/rest/getNearestSegment/{x}/{y}/1",
            segmentationSRID: 31370,

            cadmapSRID: 31370,
            cadmapVersion: 2015,

            openLocalisationPaneByDefault: true,
            openCadastralPaneByDefault: false,
            openThematicalPaneIfData: true,
            removeThematicalLayerPaneIfNoData: false,
            removeThematicalPaneIfNoResult: false,

            ignoreRelations: true,

            // identificationMethods: [{
            //     "type": "point",
            //     "label": "Cliquez sur un point ou un objet de la carte"
            // }, {
            //     "type": "line",
            //     "label": "Dessinez une ligne"
            // }, {
            //     "type": "polygon",
            //     "label": "Dessinez un polygone"
            // }, {
            //     "type": "layer",
            //     "serviceId": "PICC",
            //     "layerId": 13,
            //     "label": "Sélectionnez un arbre"
            // }, {
            //     "type": "layer",
            //     "url": "//geoservices.wallonie.be/arcgis/rest/services/PLAN_REGLEMENT/CADMAP_PARCELLES/MapServer",
            //     "layerId": 0,
            //     "label": "Sélectionnez une parcelle"
            // }, {
            //     "type": "draw-layer",
            //     "label": "Sélectionnez un dessin"
            // }],

            reportParams: null,
            // {
            //     "reportTitle": "identification !",
            // 	"url": "/geoviewer/templates/JasperTemplate.jrxml"
            // },


            globalIdentifyResults: null,

            newIdentifyResultClick: null,

            _currentHandleRelationships: null,

            allowRetryOnOffsetSymbolLayers: false,

            "widgetTitle": "Informations",
            "position": "panel-light",
            "iconClass": "infosIcon",
            "height": "auto",
            "right": "15px",
            "top": "85px",
            "resizable": true,
            "addressLabel": "Adresse approximative",
			"geocodeApiUrl" : "//geoservices.wallonie.be/geocodeWS",
            "cadmapApiUrl": "//geoservices.wallonie.be/cadmap/js/SpwCadmapApi.js",
            "altitudeLabel": "Altitude (Terrain)",
            "altitudeServiceUrl": "//geoservices.wallonie.be/arcgis/rest/services/RELIEF/WALLONIE_MNT_2013_2014/MapServer",
            "mnsLabel": "Altitude (Surface)",
            "mnsServiceUrl": "//geoservices.wallonie.be/arcgis/rest/services/RELIEF/WALLONIE_MNS_2013_2014/MapServer",

            additionalServices: null/*[{
            title: 'Cadmap',
            url: 'http://geoservices.wallonie.be/cadmap/rest/getShapeParcelleByXY/{x}/{y}',
            srid: 31370,
            resultProperty: null,
            geometryProperty: null,
            geometryFormat: 'spw',
            properties: {
                'Commune/INS': '{nomCommune} {commune}'
            }
        }, {
            title: "PICC",
            url: "http://geoservices.wallonie.be/arcgis/rest/services/TOPOGRAPHIE/PICC_VDIFF/MapServer",
            srid: 31370,
            type: "AGS_DYNAMIC",
            identifyParams: null,
            fileProperties: ['Code Nature']
        }]*/,
            additionalPanes: null,

            _toggleHandlers: null,
            _servicesOpened: null,

            ignoreFields: [],

            replaceLinks: true,
            replaceNulls: true,
            replaceFiles: false,
            accessFileService: '/geoviewer/AccessFileServlet/',
            linksName: 'Cliquez pour accéder',
            linkTest: 'http|ftp|file',
            networkFileTest: '([a-zA-Z]:)?(\\\\){1}',

            localisationOpened: true,
            cadastreOpened: false,
            exportButton: null,
            panesIdsContainingData: {},

            /**
             * @constructs
             * @param config
             */
            constructor: function (config) {
                this._toggleHandlers = [];
                this._servicesOpened = [];
                this.additionalPanes = {};
                this.additionalMapServices = [];
            },

            postMixInProperties: function(){
                this.inherited(arguments);
                require([this.cadmapApiUrl], lang.hitch(this, function(){
                    if(typeof(spwCadmap) != "undefined"){
                        spwCadmap.getVersion(lang.hitch(this, function(data){
                            this.cadmapVersion = data.version.substring(1, data.version.length);
                            this.cadastrePane.set('title', 'Références cadastrales ('+this.cadmapVersion+')');
                        }));
                    }
                }));
            },

            onIdentificationMethodChanged: function() {
                var method = null;
                this.deleteGeometry();
                if(this.identificationMethods){
                    method = this.identificationMethods[0];
                }else{
                    method = {
                        "type": "point",
                        "label": "Cliquez sur un point ou un objet de la carte"
                    }
                }

                if (this.identificationMethodsSelect) {
                    method = this.identificationMethodsSelect.get('store').get(this.identificationMethodsSelect.get('value'));
                }

                var map = this.spwViewer.get('spwMap');

                this.disableIdentification();
                this._handlers = [];

                if (method == null) {
                    MessageManager.getInstance().notifyError('Méthode d\'identification inconnue', null, 5000);
                }
                this.selectedIdentificationMethod = method;
                switch (method.type) {
                    case 'point':
                        this._handlers.push(on(map, map.events.MapClicked, lang.hitch(this, function(x, y, srid){
                            var evt = {
                                mapPoint: new Point(x, y, new SpatialReference({wkid: srid}))
                            };
                            this.saveGeometry(evt);

                            this.fillLocalisationData(evt);
                            this.identifyServices(evt);
                        })));
                        break;

                    case 'line':
                        this._handlers.push(on(this._draw, 'draw-complete', lang.hitch(this, function(evt) {
                            this.saveGeometry(evt);
                            this.fillLocalisationData(evt);
                            this.identifyServices(evt);
                        })));

                        this._draw.activate(Draw.POLYLINE);
                        break;

                    case 'polygon':
                        this._handlers.push(on(this._draw, 'draw-complete', lang.hitch(this, function(evt) {
                            this.saveGeometry(evt);
                            this.fillLocalisationData(evt);
                            this.identifyServices(evt);
                        })));

                        this._draw.activate(Draw.POLYGON);
                        break;

                    case 'draw-layer':
                        this._handlers.push(on(map, map.events.MapClicked, lang.hitch(this, function(x, y, srid) {

                            var mss = map.getMapServices({
                                type: MapServiceFactory.types.DRAW_LAYER,
                                visible: true
                            });

                            if (mss == null || mss.length < 1) {
                                MessageManager.getInstance().notifyError('Aucune couche dessin existante');
                                return;
                            }

                            var geomToCompare = GeometryUtils.buffer(new Point(x, y, new SpatialReference({wkid: srid})), 10, 'meters');

                            if (!array.some(mss, lang.hitch(this, function(ms) {

                                    if (ms.layer == null) {
                                        return;
                                    }

                                    return array.some(ms.layer.graphics, lang.hitch(this, function(g) {
                                        if (GeometryUtils.intersects(geomToCompare, g.geometry)) {
                                            var evt = {
                                                geometry: g.geometry
                                            };
                                            this.fillLocalisationData(evt);
                                            this.identifyServices(evt);
                                            this.saveGeometry(evt);
                                            return true;
                                        }

                                        return false;
                                    }));
                                }))) {
                                MessageManager.getInstance().notifyError('Aucune couche dessin trouvée à cet endroit');
                            }

                        })));

                        break;

                    case 'layer':
                        if (method.url == null && method.serviceId == null) {
                            MessageManager.getInstance().notifyError('Configuration du service erronnée (un service doit avoir une URL ou un ID)');
                            return;
                        }

                        if (method.layerId == null) {
                            MessageManager.getInstance().notifyError('Configuration du service erronnée (une couche doit être précisée)');
                            return;
                        }

                        this._handlers.push(on(map, map.events.MapClicked, lang.hitch(this, function(x, y, srid, rawEvt) {

                            if (rawEvt.ctrlKey !== true) {
                                if (this._identificationMethodFeature) {
                                    this.spwViewer.get('spwMap').get('esriMap').graphics.remove(this._identificationMethodFeature);
                                    this._identificationMethodFeature = null;
                                }
                            }

                            var evt = {
                                mapPoint: new Point(x, y, new SpatialReference({wkid: srid}))
                            };
                            var url = method.url;

                            if (method.serviceId != null) {
                                var ms = map.getMapServiceById(method.serviceId);

                                if (ms == null) {
                                    MessageManager.getInstance().notifyError('Le service précisé est introuvable');
                                    return;
                                }

                                url = ms.url;
                            }

                            this.queryGeometryForService(url + '/' + method.layerId, evt.mapPoint, rawEvt.ctrlKey).then(lang.hitch(this, function(geom) {
                                evt = {
                                    geometry: geom.geometry
                                };

                                if (rawEvt.ctrlKey !== true) {
                                    this.fillLocalisationData(evt);
                                }
                                this.saveGeometry(evt);
                                this.identifyServices(evt);
                            }));

                        })));
                        break;

                    default:
                        MessageManager.getInstance().notifyError('Méthode d\'identification inconnue', null, 5000);
                }
            },

            queryGeometryForService: function(url, pt, keepOldGeom) {
                var def = new Deferred();

                var queryTask = new QueryTask(url);

                var query = new Query();

                query.geometry = GeometryUtils.buffer(pt, 10, 'meters');
                query.outSpatialReference = {
                    wkid: 31370
                };
                query.returnGeometry = true;

                this.showLoading();

                queryTask.execute(query, lang.hitch(this, function(result) {

                    this.hideLoading();

                    if (result == null || result.features == null || result.features.length < 1) {
                        MessageManager.getInstance().notifyError('Aucune information à cet endroit');
                        return;
                    }

                    if (keepOldGeom === true) {
                        this._identificationMethodFeature = [].concat(this._identificationMethodFeature).concat(result.features[0]);
                        this.spwViewer.get('spwMap').highlightFeature(this._identificationMethodFeature);
                    }
                    else {
                        this._identificationMethodFeature = result.features[0];
                        this.spwViewer.get('spwMap').highlightFeature(this._identificationMethodFeature);
                    }

                    def.resolve(result.features[0]);

                }), lang.hitch(this, function(err) {

                    this.hideLoading();

                    console.error(err);
                    MessageManager.getInstance().notifyError('Impossible de récupérer les informations du service (erreur serveur)');

                }));


                return def;
            },

            disableIdentification: function() {
                array.forEach(this._handlers, lang.hitch(this, function(h) {
                    h.remove();
                }));

                this._handlers = [];

                if(this._draw && this._draw._activated){
                    this._draw.deactivate();
                }

                if (this._identificationMethodFeature) {
                    this.spwViewer.get('spwMap').get('esriMap').graphics.remove(this._identificationMethodFeature);
                    this._identificationMethodFeature = null;
                }
            },

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

                if(this.reportParams) {
                    this.spwViewer.get('spwMap').get('esriMap').on('click', lang.hitch(this, function(){
                        this.newIdentifyResultClick = true;
                    }))
                    this.exportButtonAttachedPoint.addEventListener('click', lang.hitch(this, function(){
                        this.createReport();
                    }))
                } else {
                    this.exportButtonAttachedPoint.style.display = "none";
                }

                this._draw = new Draw(this.spwViewer.get('spwMap').get('esriMap'));

                if (this.identificationMethods && this.identificationMethods.length > 1) {
                    this.identificationMethodsSelect = new Select({
                        searchAttr: 'label',
                        labelAttr: 'label',
                        sortByLabel: false,
                        store: new Memory({
                            data: array.map(this.identificationMethods, function(method, idx) {
                                return lang.mixin(method, {
                                    id: idx+1
                                });
                            }),
                            idProperty: 'id'
                        }),
                        'style': 'display: inline-block'
                    }, this._identificationMethodNode);

                    //this.identificationMethodsSelect.startup();

                    this.identificationMethodsSelect.on('change', lang.hitch(this, this.onIdentificationMethodChanged));
                }
                else if(this.identificationMethods){
                    this._identificationMethodNode.innerHTML = this.identificationMethods[0].label;
                } else {
                    this._identificationMethodNode.innerHTML = "Cliquez sur un point ou un objet de la carte";
                    this.identificationMethods = [{
                        type: 'point',
                        label: 'Cliquez sur un point ou un objet de la carte'
                    }];
                }

                if (this.informationVisible == null) {
                    domStyle.set(this.cadastrePane.domNode, 'display', 'none');
                    domStyle.set(this._localisationTitlePane.domNode, 'display', 'none');
                }
                else {
                    domStyle.set(this._addressContainerNode, 'display', this.informationVisible.indexOf('address') < 0 ? 'none' : '');
                    domStyle.set(this._coordinatesContainerNode, 'display', this.informationVisible.indexOf('coordinates') < 0 ? 'none' : '');
                    domStyle.set(this._lambertContainerNode, 'display', this.informationVisible.indexOf('coordinates') < 0 ? 'none' : '');
                    domStyle.set(this._altitudeContainerNode, 'display', this.informationVisible.indexOf('altitude') < 0 ? 'none' : '');
                    domStyle.set(this._mnsContainerNode, 'display', this.informationVisible.indexOf('mns') < 0 ? 'none' : '');
                    domStyle.set(this._segmentContainerNode, 'display', this.informationVisible.indexOf('segmentation') < 0 ? 'none' : '');

                    if (!this.informationVisible.join('').match(/address|coordinates|altitude|segmentation/)) {
                        domStyle.set(this._localisationTitlePane.domNode, 'display', 'none');
                    }

                    domStyle.set(this.cadastrePane.domNode, 'display', this.informationVisible.indexOf('cadastre') < 0 ? 'none' : '');
                }

                var localisationPaneToggleHandler = aspect.after(this._localisationTitlePane, 'toggle', lang.hitch(this, function(){
                    this.openLocalisationPaneByDefault = this._localisationTitlePane.open
                }));
                this.own(localisationPaneToggleHandler);

                var cadastralPaneToggleHandler = aspect.after(this.cadastrePane, 'toggle', lang.hitch(this, function(){
                    this.openCadastralPaneByDefault = this.cadastrePane.open
                }));
                this.own(cadastralPaneToggleHandler);
            },

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

            deleteGeometry: function(){
                this.currentGeometry = null;
            },

            getIdentifyDataForReport: function(evt) {
                this.thereIsSomethingToPrint = false;
                this._clearHandlers();
                var services = this.spwViewer.get('spwMap').getMapServices({ isBaseMap: false, visible: true }), layerPanes = {};
                var promises = [];
                var reportPromises = [];
                var servicesInError = [];
                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();
                            }),
                            lang.hitch(this, function(service){
                                servicesInError.push(service);
                                def.resolve();
                            }))
                    );
                }));

                all(promises).then(function(){
                    if(servicesInError.length > 0){
                        var servicesLabel = [];
                        array.forEach(servicesInError, lang.hitch(this, function(serv){
                            servicesLabel.push(serv.label ? serv.label : serv.serviceId);
                        }))
                        var errorMessage = "Une erreur est survenue lors de l'identification de ces services: "+ servicesLabel.join();
                        MessageManager.getInstance().notifyError('', errorMessage);
                    }
                });

                return reportPromises;
            },

            createReport: function() {
                var localizationReportDataParams = {
            		geocodeApiUrl: this.geocodeApiUrl,
                    geolocalisationSRI : this.geolocalisationSRI,
                    altitudeServiceUrl : this.altitudeServiceUrl,
                    mnsServiceUrl : this.mnsServiceUrl,
                    cadmapApiUrl : this.cadmapApiUrl,
                    cadmapSRID : this.cadmapSRID,
                    maxSquareAreaForCadastralReport: this.maxSquareAreaForCadastralReport,
                    identificationType: this.selectedIdentificationMethod.type
                };
                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, this.ignoreFields).then(lang.hitch(this, function(identifyResults){
                    MessageManager.getInstance().hideModalMessage();
                    Utils.createReport(this.currentGeometry,localizationReportDataParams, this.reportParams, identifyResults, this.spwViewer, this.reportWithLegend);
                }));
            },

            showNoIdentifyResultsMessage: function() {
                MessageManager.getInstance().notifyInfo("","Aucun résultat trouvé lors du carottage, l'impression est annulée.", 5000);
            },

            showNoGeometryMessage: function() {
                MessageManager.getInstance().notifyInfo("","Aucune géométrie trouvée pour le carrotage. Veuillez dessiner une géométrie sur la carte.", 5000);
            },

            onActivate: function(){
                this.inherited(arguments);
                this.onIdentificationMethodChanged();
            },

            onDeactivate: function() {
                this.inherited(arguments);
                this.disableIdentification();
            },

            isLink: function(prop) {
                return new RegExp('^(' + this.linkTest + ')').test(prop);
            },

            isNetworkFile: function(prop) {
                return new RegExp('^(' + this.networkFileTest + ')').test(prop);
            },

            showDataLoading: function(){
                array.forEach(arguments, lang.hitch(this, function(domNode){
                    domConstruct.empty(domNode);
                    domConstruct.create("img", { style:"width:11px; height: 11px;", src: this.get('imagesPath') + "/ajax-loader.gif" }, domNode);
                }));
            },

            fillLocalisationData: function(evt) {
                if (this.informationVisible) {
                    if (this.informationVisible.indexOf('address') > -1) {
                        this.fillAdress(evt);
                    }

                    if (this.informationVisible.indexOf('segmentation') > -1) {
                        this.fillSegment(evt);
                    }

                    if (this.informationVisible.indexOf('coordinates') > -1) {
                        this.fillCoordinates(evt);
                    }

                    if (this.informationVisible.indexOf('altitude') > -1) {
                        this.fillAltitude(evt);
                    }

                    if (this.informationVisible.indexOf('mns') > -1) {
                        this.fillMNS(evt);
                    }

                    if (this.informationVisible.indexOf('cadastre') > -1) {
                        this.fillCadastre(evt);
                    }
                }

                this.fillAdditionalServices(evt);
            },

            fillAdditionalServices: function(evt) {
                var mapSRID = this.spwViewer.get('spwMap').getSpatialReferenceSRID();
                array.forEach(this.additionalServices, lang.hitch(this, function(additionalService, index) {
                    var titlePane = this.additionalPanes[additionalService.title + index];

                    if (titlePane == null) {
                        titlePane = new TitlePane({
                            title: additionalService.title,
                            content: domConstruct.create("img", { style:"width:11px; height: 11px;", src: this.get('imagesPath') + "/ajax-loader.gif" }),
                            open: additionalService.opened
                        }, domConstruct.create("div", null, this.identifiedServicesDomItems, 'before'));

                        this.additionalPanes[additionalService.title + index] = titlePane;
                    }

                    var pt = evt.mapPoint;

                    if (additionalService.srid && additionalService.srid !== pt.spatialReference.wkid) {
                        pt = ProjectionManager.getInstance().transform(pt.spatialReference.wkid, additionalService.srid, pt);
                    }

                    if (additionalService.type == null || additionalService.type === 'rest') {
                        request({
                            url: lang.replace(additionalService.url, pt),
                            handleAs: 'json',
                            headers: {
                                'Content-Type': null
                            }
                        }).then(lang.hitch(this, function(response) {
                            var datasWrapper;

                            if(titlePane.contentAdded){
                                datasWrapper = titlePane.containerNode.children[0];
                            } else {
                                datasWrapper = domConstruct.create("div", {
                                    "class":"subContent",
                                    "style": "padding-left: 5px;"
                                });
                                titlePane.set('content', datasWrapper);
                                titlePane.contentAdded = true;
                            }

                            domConstruct.empty(datasWrapper);

                            var results = response;

                            if (additionalService.resultProperty) {
                                results = lang.getObject(additionalService.resultProperty, null, results);
                            }

                            results = [].concat(results);

                            array.forEach(results, lang.hitch(this, function(result, idx) {

                                if (idx < results.length - 1) {
                                    domConstruct.create('hr', {
                                        'class': 'itemSeparator'
                                    }, datasWrapper, 'last');
                                }

                                var table = domConstruct.create("table", {
                                    style: 'word-break: break-word; width: 100%;'
                                }, datasWrapper);

                                var geom = lang.getObject(additionalService.geometryProperty, null, result);
                                var feature = null;

                                if (geom) {
                                    feature = this.parseGeometry(geom, additionalService.geometryFormat, additionalService.srid);

                                    if (feature) {
                                        this._addHandlers({
                                            node: table,
                                            feature: feature
                                        });
                                    }
                                }

                                var dataWrapper = domConstruct.create("tbody", null, table);

                                var cpt = 0;

                                for (var k in additionalService.properties) {
                                    if (!additionalService.properties.hasOwnProperty(k)) {
                                        continue;
                                    }

                                    var val = lang.replace(additionalService.properties[k], result);

                                    var rowWrapper = domConstruct.create("tr", {}, dataWrapper);

                                    if (cpt === 0 && feature) {
                                        this._addZoomIcon({
                                            node: domConstruct.create("td", null, rowWrapper),
                                            feature: feature
                                        });
                                    }
                                    else {
                                        domConstruct.create("td", null, rowWrapper);
                                    }

                                    domConstruct.create("td", {
                                        innerHTML: k + " : ",
                                        style: "font-weight: bold;min-width:75px;"
                                    }, rowWrapper);

                                    if ((this.replaceLinks && this.isLink(val)) || (additionalService.fileProperties && additionalService.fileProperties.indexOf(k)  > -1)) {
                                        if (additionalService.fileProperties && additionalService.fileProperties.indexOf(k) > -1) {
                                            val = this.addLinkProtocol(val, 'file');
                                        }

                                        domConstruct.create("a", {
                                            href: val,
                                            innerHTML: this.linksName,
                                            target: '_blank'
                                        }, domConstruct.create("td", null, rowWrapper));
                                    }
                                    else if (this.replaceFiles && (
                                            (additionalService.networkFileProperties && additionalService.networkFileProperties.indexOf(k) > -1) || this.isNetworkFile(val)
                                        )) {
                                        domConstruct.create('a', {
                                            href: this.accessFileService + val,
                                            innerHTML: this.linksName,
                                            target: '_blank'
                                        }, domConstruct.create("td", null, rowWrapper));
                                    }
                                    else {
                                        domConstruct.create("td", { innerHTML: this.replaceNullsFunc(val) }, rowWrapper);
                                    }
                                }

                            }));

                        }), lang.hitch(this, function(err) {
                            console.error(err);
                        }));
                    }
                    else {
                        var mapService = this.additionalMapServices[additionalService.title + index];

                        if (mapService == null) {
                            var mapService = MapServiceFactory.createService(lang.mixin(additionalService, {identifiable: true, spwMap: this.spwViewer.get('spwMap')}));
                            this.additionalMapServices[additionalService.title + index] = mapService;
                        }

                        if (mapService.get('loaded')) {
                            this._identifyAdditionalMapService(mapService, titlePane, pt);
                        }
                        else {
                            on.once(mapService, mapService.events.MapServiceLoaded, lang.hitch(this, function() {
                                this._identifyAdditionalMapService(mapService, titlePane, pt);
                            }));
                        }
                    }

                }));
            },

            addLinkProtocol: function(url, protocol) {
                if (url.indexOf(protocol + ':') === 0) {
                    return url;
                }

                return protocol + '://' + (url.indexOf('//') === 0 ? url.substring(2) : url);
            },

            _identifyAdditionalMapService: function(mapService, titlePane, point) {
                var layerPanes = {};
                var serviceTitlePaneContent = new ContentPane({style: 'height: 100%;'});

                for(var key in mapService.mapServiceLayers) {
                    if(mapService.mapServiceLayers[key].get('identifiable') && mapService.mapServiceLayers[key].get('subLayers').length == 0 &&
                        mapService.mapServiceLayers[key].isVisible() && mapService.mapServiceLayers[key].visibleAtScale(mapService.spwMap.getCurrentScale())) {
                        var layerId = mapService.mapServiceLayers[key].layerId;
                        var layerPane = new TitlePane({
                            title: (mapService.mapServiceLayers[key].name ? mapService.mapServiceLayers[key].name : 'Donnée sans nom'),
                            content: domConstruct.create("img", { style:"width:11px; height: 11px;", src: this.get('imagesPath') + "/ajax-loader.gif" }),
                            open: mapService.open
                        }, domConstruct.create("div", null, serviceTitlePaneContent.domNode, 'last'));

                        layerPanes[mapService.serviceId + "-" + mapService.mapServiceLayers[key].get('layerId')] = layerPane;
                    }
                }

                titlePane.set('content', serviceTitlePaneContent);

                var hasOneTable = {};

                mapService.identify({
                    mapPoint: point,
                    ignoreFields: this.ignoreFields,
                    ignoreRelations: this.ignoreRelations
                }, lang.hitch(this, function(identifyResults, service, data){
                    this.displayIdentifyResult(identifyResults, service, data, layerPanes, hasOneTable);
                }));
            },

            parseGeometry: function(geom, format, srid) {
                if (format == null) {
                    return null;
                }

                format = format.toLowerCase();

                var mapSRID = this.spwViewer.get('spwMap').getSpatialReferenceSRID();

                if (format === 'spw') {
                    geom = this._rawDataToGeom(geom);
                }
                else if (format === 'geojson') {
                    geom = GeometryConverter.geoJSONToEsri(geom);
                }
                else if (format === 'wkt') {
                    geom = GeometryConverter.wktToEsri(geom);
                }
                else if (format !== 'esri') {
                    return null;
                }

                if (geom == null) {
                    return null;
                }

                geom.setSpatialReference(new SpatialReference({wkid: srid}));

                if (srid !== mapSRID) {
                    geom = ProjectionManager.getInstance().transform(srid, mapSRID, geom);
                }

                return new Graphic(geom);
            },

            getPoint: function(evt, srid) {
                var pt = null;

                if (evt.mapPoint) {
                    pt = evt.mapPoint;
                }
                else if (evt.geometry) {
                    if (evt.geometry.getCentroid) {
                        pt = evt.geometry.getCentroid();
                    }
                    else if (evt.geometry.type === 'polyline') {
                        pt = evt.geometry.getExtent().getCenter();
                    }
                    else if (evt.geometry.type === 'point') {
                        pt = evt.geometry;
                    }
                }

                return ProjectionManager.getInstance().projectPoint(pt.spatialReference.wkid, srid,
                    pt.x, pt.y);
            },

            fillAdress: function(evt){
                this.showDataLoading(this.adressContent);
                Utils.getAddress(evt, this.geocodeApiUrl, this.geolocalisationSRID).then(
                    lang.hitch(this, function(data){
                        if (data && data.candidates && data.candidates.length > 0) {
                        	var c = data.candidates[0];
                        	if(c.house) this.adressContent.innerHTML = '<p>' + c.street.name + ', ' + c.house.name + '<br>' + c.city.name + '</p>';
                        	else if(c.street) this.adressContent.innerHTML = '<p>' + c.street.name + '<br>' + c.city.name + '</p>';
                        	else if(c.city) this.adressContent.innerHTML = '<p>' + c.city.name + '</p>';
                        	else this.adressContent.innerHTML = "Pas de donnée trouvée";
                        } else {
                        	this.adressContent.innerHTML = "Pas de donnée trouvée";
                        }
                    }),
                    lang.hitch(this, function(error){
                        this.adressContent.innerHTML = "Erreur du service de localisation";
                    }))
            },

            fillSegment: function(evt) {
                this.showDataLoading(this.segmentCode, this.segmentBk, this.segmentDistance);

                domStyle.set(this.segmentTable, 'display', '');
                domStyle.set(this.segmentError, 'display', 'none');

                var showSegmentError = function(err) {
                    domStyle.set(this.segmentTable, 'display', 'none');
                    domStyle.set(this.segmentError, 'display', '');
                    this.segmentError.innerHTML = 'Erreur du service de segmentation';
                    err && console.error(err);
                };

                var pt = this.getPoint(evt, this.segmentationSRID);

                pt.x = Math.round(pt.x);
                pt.y = Math.round(pt.y);

                request({
                    url: lang.replace(this.segmentationApiUrl, pt),
                    handleAs: 'json',
                    headers: {
                        'Content-Type': null
                    }
                }).then(lang.hitch(this, function(response) {
                        if (response.errorCode) {
                            showSegmentError(response);
                            return;
                        }

                        var segment = response.nearestSegment;

                        if (segment == null) {
                            showSegmentError('aucun segment trouvé');
                            return;
                        }

                        if (segment.geometry) {
                            var geom = GeometryConverter.wktToEsri(segment.geometry);
                            geom.setSpatialReference({wkid: this.segmentationSRID});

                            if (geom.spatialReference.wkid !== this.spwViewer.get('spwMap').getSpatialReferenceSRID()) {
                                geom = ProjectionManager.getInstance().transform(geom.spatialReference.wkid, this.spwViewer.get('spwMap').getSpatialReferenceSRID());
                            }

                            this._addZoomIcon({
                                node: this.segmentZoomNode,
                                feature: new Graphic(geom),
                                inline: true
                            });
                        }
                        this.segmentCode.innerHTML = segment.code;
                        this.segmentBk.innerHTML = (segment.mesure / 1000).toFixed(3);
                        this.segmentDistance.innerHTML = (Math.round(segment.distance * 100) / 100) + ' (m)';
                    }),
                    lang.hitch(this, function(err) {
                        showSegmentError(err);
                    }));
            },

            fillCoordinates: function(evt){
                this.showDataLoading(this.longitudeContent, this.latitudeContent, this.lambertXContent, this.lambertYContent);

                var pt = this.getPoint(evt, 4326);

                this.longitudeContent.innerHTML = (Math.round(pt.x * 100000) / 100000).toString().replace('.', ',');
                this.latitudeContent.innerHTML = (Math.round(pt.y * 100000) / 100000).toString().replace('.', ',');

                var projPt = ProjectionManager.getInstance().projectPoint(4326, 31370, pt.x, pt.y);
                this.lambertXContent.innerHTML = (Math.round(projPt.x)).toString().replace('.', ',');
                this.lambertYContent.innerHTML = (Math.round(projPt.y)).toString().replace('.', ',');
            },

            fillAltitude: function(evt){
                this.showDataLoading(this.altitudeContent);

                var identifyParams = new IdentifyParameters();
                identifyParams.tolerance = 1;
                identifyParams.spatialReference = evt.mapPoint ? evt.mapPoint.spatialReference : evt.geometry.spatialReference;
                identifyParams.width = this.spwViewer.get('spwMap').get('esriMap').width;
                identifyParams.height = this.spwViewer.get('spwMap').get('esriMap').height;
                identifyParams.geometry = evt.mapPoint ? evt.mapPoint : evt.geometry;
                identifyParams.mapExtent = this.spwViewer.get('spwMap').get('esriMap').extent;

                Utils.getAltitude(identifyParams, this.altitudeServiceUrl).then(
                    lang.hitch(this, function(identifyResult) {
                        if(identifyResult && identifyResult.length > 0){
                            var alti = Math.round(identifyResult[0].feature.attributes['Pixel Value'].replace(',','.') * 100)/100;
                            this.altitudeContent.innerHTML = isNaN(alti) ? "Valeur inconnue" : alti.toString().replace('.', ',');
                        } else {
                            this.altitudeContent.innerHTML = "Valeur inconnue";
                        }
                    }), function(error) {
                        console.log("Identify Error : ", error);
                        this.altitudeContent.innerHTML = "Erreur du service d'altitude";
                        return null;
                    });
            },

            fillMNS: function(evt){
                this.showDataLoading(this.mnsContent);

                var identifyParams = new IdentifyParameters();
                identifyParams.tolerance = 1;
                identifyParams.spatialReference = evt.mapPoint ? evt.mapPoint.spatialReference : evt.geometry.spatialReference;
                identifyParams.width = this.spwViewer.get('spwMap').get('esriMap').width;
                identifyParams.height = this.spwViewer.get('spwMap').get('esriMap').height;
                identifyParams.geometry = evt.mapPoint ? evt.mapPoint : evt.geometry;
                identifyParams.mapExtent = this.spwViewer.get('spwMap').get('esriMap').extent;

                Utils.getAltitude(identifyParams, this.mnsServiceUrl).then(
                    lang.hitch(this, function(identifyResult) {
                        if(identifyResult && identifyResult.length > 0){
                            var alti = Math.round(identifyResult[0].feature.attributes['Pixel Value'].replace(',','.') * 100)/100;
                            this.mnsContent.innerHTML = isNaN(alti) ? "Valeur inconnue" : alti.toString().replace('.', ',');
                        } else {
                            this.mnsContent.innerHTML = "Valeur inconnue";
                        }
                    }), function(error) {
                        console.log("Identify Error : ", error);
                        this.mnsContent.innerHTML = "Erreur du service MNS";
                        return null;
                    });
            },

            fillCadastre: function(evt){
                this.showDataLoading(this.cadCommuneContent, this.cadDivisionContent, this.cadSectionContent, this.cadRadicalContent, this.cadExposantContent, this.cadPuissanceContent, this.cadBisContent);

                this._removeHandlers(this.cadastrePane);

                Utils.getCadastre(evt, this.cadmapApiUrl, this.cadmapSRID).then(
                    lang.hitch(this, function(data){
                        if(data){
                            var feature = this._rawDataToFeature(data);

                            this._addHandlers({
                                node: this.cadastreTableNode,
                                feature: feature
                            });

                            this._addZoomIcon({
                                node: this.cadastreZoomNode,
                                feature: feature
                            });

                            this.cadCommuneContent.innerHTML = data.nomCommune + " " + data.commune;
                            this.cadDivisionContent.innerHTML = data.divNom;
                            this.cadSectionContent.innerHTML = data.sect;
                            this.cadRadicalContent.innerHTML = data.radical;
                            this.cadExposantContent.innerHTML = data.exposant;
                            this.cadPuissanceContent.innerHTML = data.puissance;
                            this.cadBisContent.innerHTML = data.bis;
                        } else {
                            this.cadCommuneContent.innerHTML = "N/A";
                            this.cadDivisionContent.innerHTML = "N/A";
                            this.cadSectionContent.innerHTML = "N/A";
                            this.cadRadicalContent.innerHTML = "N/A";
                            this.cadExposantContent.innerHTML = "N/A";
                            this.cadPuissanceContent.innerHTML = "N/A";
                            this.cadBisContent.innerHTML = "N/A";
                        }
                    }),
                    lang.hitch(this, function(error){
                        this.cadCommuneContent.innerHTML = "Erreur du service du cadastre";
                        this.cadDivisionContent.innerHTML = "";
                        this.cadSectionContent.innerHTML = "";
                        this.cadRadicalContent.innerHTML = "";
                        this.cadExposantContent.innerHTML = "";
                        this.cadPuissanceContent.innerHTML = "";
                        this.cadBisContent.innerHTML = "";
                    })
                )
            },

            _clearHandlers: function() {
                array.forEach(this._toggleHandlers, function(t) {
                    t.remove();
                });

                this._toggleHandlers = [];
            },

            _toggleService: function(id) {
                var idx = this._servicesOpened.indexOf(id);

                if (idx >= 0) {
                    this._servicesOpened.splice(idx, 1);
                }
                else {
                    this._servicesOpened.push(id);
                }
            },

            _getScrollPosition: function() {
                return this.scrollContainerNode.scrollTop;
            },

            _setScrollPosition: function(pos) {
                this.scrollContainerNode.scrollTop = pos;
            },

            identifyServices: function(evt){

                this.cadastrePane.set('open', this.openCadastralPaneByDefault);
                this._localisationTitlePane.set('open', this.openLocalisationPaneByDefault);

                var scrollPos = this._getScrollPosition();

                domConstruct.empty(this.identifiedServicesDomItems);
                this._clearHandlers();

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

                this._currentHandleRelationships = this.handleRelationships;
                if(services && services.length > 0){
                    array.forEach(services, lang.hitch(this, function(serv){
                        if(serv.params.handleRelationships && serv.params.handleRelationships == true){
                            this._currentHandleRelationships = true;
                        }
                    }))
                }

                var promises = [];

                array.forEach(services, lang.hitch(this, function(service) {
                    var serviceTitlePaneContent = new ContentPane({style: 'height: 100%;'});
                    var atLeastOne = false;
                    for(var key in service.mapServiceLayers){
                        if(service.mapServiceLayers[key].get('identifiable') && service.mapServiceLayers[key].get('subLayers').length == 0 && service.mapServiceLayers[key].isVisible() && service.mapServiceLayers[key].visibleAtScale(service.spwMap.getCurrentScale())){
                            var layerId = service.mapServiceLayers[key].layerId;

                            var titlePane = new TitlePane({
                                title: (service.mapServiceLayers[key].name ? service.mapServiceLayers[key].name : 'Donnée sans nom'),
                                content: domConstruct.create("img", { style:"width:11px; height: 11px;", src: this.get('imagesPath') + "/ajax-loader.gif" }),
                                open: this._servicesOpened.indexOf(layerId) > -1
                            }, domConstruct.create("div", null, serviceTitlePaneContent.domNode, 'last'));

                            var handler = aspect.after(titlePane, 'toggle', lang.hitch(this, this._toggleService, layerId));

                            this._toggleHandlers.push(handler);
                            this.own(handler);

                            atLeastOne = true;
                            layerPanes[service.serviceId + "-" + service.mapServiceLayers[key].get('layerId')] = titlePane;
                        }
                    }

                    if (atLeastOne || (service instanceof GraphicsMapService && service.identifiable && service.layer.visible && service.layer.isVisibleAtScale(this.spwViewer.spwMap.getCurrentScale()))) {
                        var serviceTitlePane = new TitlePane({
                            title: service.label,
                            content: serviceTitlePaneContent,
                            open: this._servicesOpened.indexOf(service.serviceId) > -1
                        }, domConstruct.create('div', null, this.identifiedServicesDomItems));

                        layerPanes[service.serviceId] = serviceTitlePane;

                        var serviceTitlePaneHandler = aspect.after(serviceTitlePane, 'toggle', lang.hitch(this, this._toggleService, service.serviceId));

                        this._toggleHandlers.push(serviceTitlePaneHandler);
                        this.own(serviceTitlePaneHandler);

                        if (service instanceof GraphicsMapService) {
                            layerPanes[service.serviceId + "-" + service.layer.id] = serviceTitlePane;
                        }
                    }

                    var hasOneTable = {};

                    promises.push(
                        service.identify(lang.mixin(evt, {
                            ignoreFields: this.ignoreFields,
                            tolerance: 10,
                            allowRetryOnOffsetSymbolLayers: this.allowRetryOnOffsetSymbolLayers
                        }), lang.hitch(this, function(identifyResults, service, data){
                            this.displayIdentifyResult(identifyResults, service, data, layerPanes, hasOneTable);
                        }))
                    );
                }));

                all(promises).then(lang.hitch(this, function() {
                    this._setScrollPosition(scrollPos);
                }));
            },

            _rawDataToGeom: function(data) {
                if(data.polygones) {
                    var polygon = new Polygon(this.spwViewer.get('spatialReference'));

                    for (var i = 0; i < data.polygones.length; ++i) {
                        var points = new Array();

                        if(data.polygones[i].coordonnees) {
                            for(var j=0; j<data.polygones[i].coordonnees.length; j++) {
                                if (polygon.spatialReference.wkid !== this.cadmapSRID) {
                                    var tmp = new Point(data.polygones[i].coordonnees[j].x, data.polygones[i].coordonnees[j].y, new SpatialReference(this.cadmapSRID));
                                    points.push(ProjectionManager.getInstance().transform(this.cadmapSRID, polygon.spatialReference.wkid, tmp));
                                }
                                else {
                                    points.push(new Point(data.polygones[i].coordonnees[j].x, data.polygones[i].coordonnees[j].y, this.spwViewer.get('spatialReference')));
                                }
                            }
                        }

                        polygon.addRing(points);
                    }

                    return polygon;
                }

                return null;
            },

            _rawDataToFeature: function(data) {
                var geom = this._rawDataToGeom(data);

                if (geom) {
                    return new Graphic(geom, this.symbol);
                }

                return null;
            },

            _removeHandlers: function(node) {
                if (node == null) {
                    return;
                }

                if (node.mouseEnterHandler) {
                    node.mouseEnterHandler.remove();
                    node.mouseEnterHandler = null;
                }

                if (node.mouseLeaveHandler) {
                    if (node.feature) {
                        this.spwViewer.get('spwMap').removeFeature(node.feature);
                    }

                    node.mouseLeaveHandler.remove();
                    node.mouseLeaveHandler = null;
                }
            },

            _addHandlers: function(opts) {
                if (opts == null || opts.node == null) {
                    return;
                }

                var node = opts.node;

                this._removeHandlers(node);

                if (opts.feature == null) {
                    return;
                }

                this.own(
                    node.mouseEnterHandler = on(node, mouse.enter, lang.hitch(this, function() {
                        this.spwViewer.get('spwMap').highlightFeature(opts.feature);
                    })),

                    node.mouseLeaveHandler = on(node, mouse.leave, lang.hitch(this, function() {
                        this.spwViewer.get('spwMap').removeFeature(opts.feature);
                    }))
                );

                node.feature = opts.feature;
            },

            _addZoomIcon: function(opts) {
                if (opts == null || opts.node == null) {
                    return;
                }

                var node = opts.node;

                if (node.zoomHandler) {
                    node.zoomHandler.remove();
                    node.zoomHandler = null;
                }

                var zoomIcon = node.zoomIcon;

                if (zoomIcon == null) {
                    zoomIcon = domConstruct.create('div', {
                        'class': 'zoomImg'
                    }, node, 'last');

                    node.zoomIcon = zoomIcon;
                }

                if (opts.feature == null) {
                    domStyle.set(node.zoomIcon, 'display', 'none');
                    return;
                }

                domStyle.set(node.zoomIcon, 'display', opts.inline ? 'inline-block' : '');

                var timeout = null;
                this.own(
                    node.zoomHandler = on(zoomIcon, touch.press, lang.hitch(this, function(event) {
                        this.spwViewer.get('spwMap').zoomToFeature(opts.feature);
                        if (opts.highlight) {
                            this.spwViewer.get('spwMap').highlightFeature(opts.feature);
                            clearTimeout(timeout);
                            timeout = setTimeout(lang.hitch(this, function() {
                                this.spwViewer.get('spwMap').unhighlightFeature(opts.feature);
                                this.spwViewer.get('spwMap').get('esriMap').graphics.remove(opts.feature);
                            }), 2000);
                        }

                        event.stopPropagation();
                    }))
                );
            },

            displayIdentifyResult: function(identifyResults, service, data, panes, hasOneTable){
                // if(this.globalIdentifyResults == null){
                //     this.globalIdentifyResults = [];
                // }
                // if(this.newIdentifyResultClick){
                //     this.globalIdentifyResults = [];
                //     this.newIdentifyResultClick = false;
                // }
                // this.globalIdentifyResults.push({service: service, results: identifyResults, data: data});

                if (service == null) {
                    return ;
                }

                if (this.removeThematicalPaneIfNoResult && identifyResults != null && identifyResults.length == 0) {
                    if (panes[service.serviceId] != null) {
                        domConstruct.empty(panes[service.serviceId].domNode.id);
                    }
                }

                for(var k in service.mapServiceLayers){
                    if(panes[service.serviceId + "-" + service.mapServiceLayers[k].layerId]){
                        panes[service.serviceId + "-" + service.mapServiceLayers[k].layerId].set('content', domConstruct.create("div", { innerHTML: "Aucune donnée dans cette zone", "class":"subContent", style: "padding: 10px 30px;"}));
                        panes[service.serviceId + "-" + service.mapServiceLayers[k].layerId].set('open', false);
                        this._removeHandlers(panes[service.serviceId + "-" + service.mapServiceLayers[k].layerId]);
                    }
                }

                if (service instanceof GraphicsMapService) {
                    if(panes[service.serviceId + "-" + service.layer.id]) {
                        panes[service.serviceId + "-" + service.layer.id].set('content', domConstruct.create("div", { innerHTML: "Aucune donnée dans cette zone", "class":"subContent", style: "padding: 10px 30px;"}));
                        this._removeHandlers(panes[service.serviceId + "-" + service.layer.id]);
                    }
                }

                if(data && data.length > 0) {

                    array.forEach(data, lang.hitch(this, function(d, idx){
                        var datasWrapper;

                        if (panes[service.serviceId + "-" + d.layerId] == null) {
                            return;
                        }

                        if(panes[service.serviceId + "-" + d.layerId].contentAdded){
                            datasWrapper = panes[service.serviceId + "-" + d.layerId].containerNode.children[0];
                        } else {
                            datasWrapper = domConstruct.create("div", {
                                "class":"subContent",
                                "style": "padding-left: 5px;"
                            });
                            if (this.removeThematicalLayerPaneIfNoData) {
                                panes[service.serviceId + "-" + d.layerId]['mustBeDestroy'] = false;
                            }
                            if (panes[service.serviceId + "-" + d.layerId]) {
                                panes[service.serviceId + "-" + d.layerId].set('content', datasWrapper);
                                panes[service.serviceId + "-" + d.layerId].contentAdded = true;
                                panes[service.serviceId + "-" + d.layerId].set('open', this.openThematicalPaneIfData && true);
                            }
                            if (panes[service.serviceId]) {
                                panes[service.serviceId].set('open', this.openThematicalPaneIfData && true);
                                panes[service.serviceId]['mustBeDestroy'] = false;
                            }
                        }

                        if (hasOneTable[service.serviceId + "-" + d.layerId]) {
                            domConstruct.create('hr', {
                                'class': 'itemSeparator'
                            }, datasWrapper, 'last');
                        }

                        var table = domConstruct.create("table", {
                            style: 'word-break: break-word; width: 100%;'
                        }, datasWrapper);

                        if (identifyResults[idx]) {
                            this._addHandlers({
                                node: table,
                                feature: identifyResults[idx].feature
                            });
                        }
                        else {
                            this._removeHandlers(table);
                        }

                        var dataWrapper = domConstruct.create("tbody", null, table);
                        var mapServiceLayer = service.getMapServiceLayer(d.layerId);

                        var cpt = 0;
                        for(var k in d.data){
                            if (!d.data.hasOwnProperty(k)) {
                                continue;
                            }

                            if(d.data[k] instanceof Object){
                                var rowWrapper = domConstruct.create("tr", {}, dataWrapper);

                                if (cpt === 0 && identifyResults[idx]) {
                                    this._addZoomIcon({
                                        node: domConstruct.create("td", null, rowWrapper),
                                        feature: identifyResults[idx].feature
                                    });
                                    cpt += 1;
                                }
                                else {
                                    domConstruct.create("td", null, rowWrapper);
                                }

                                domConstruct.create("td", { innerHTML: '', style: 'display: none'}, rowWrapper);

                                //If data[k] is an object
                                if(d.data[k] != null && d.data[k].length > 0 && this._currentHandleRelationships){

                                    var cell = domConstruct.create('td', {'colspan':'2'}, rowWrapper, 'last');
                                    //For each relationship
                                    array.forEach(d.data[k], lang.hitch(this, function(relation){
                                        var content = domConstruct.create('table', { style:"width: 100%"});
                                        var tbody = domConstruct.create('tbody', null, content);
                                        var i = 0, zoomNode;

                                        for(var key in relation){
                                            var row = domConstruct.create('tr', null, tbody);
                                            var firstTd = domConstruct.create('td', {}, row);
                                            if(i === 0){
                                                zoomNode = firstTd;
                                            }
                                            domConstruct.create('td', { style:"font-weight: bold; text-transform: capitalize;", innerHTML: key + ' : '}, row);
                                            domConstruct.create('td', { innerHTML: relation[key]}, row);
                                            i ++;
                                        }

                                        var relationTitlePane = new TitlePane({
                                            title: k,
                                            content: content,
                                            open: true
                                        }, domConstruct.create('div', null, cell, 'last'));
                                    }));
                                }
                            }else{
                                var rowWrapper = domConstruct.create("tr", {}, dataWrapper);

                                if (cpt === 0 && identifyResults[idx]) {
                                    this._addZoomIcon({
                                        node: domConstruct.create("td", null, rowWrapper),
                                        feature: identifyResults[idx].feature
                                    });
                                    cpt+=1;
                                }
                                else {
                                    domConstruct.create("td", null, rowWrapper);
                                }

                                domConstruct.create("td", { innerHTML: k.toString() + " : ", style: "font-weight: bold;min-width:75px;" }, rowWrapper);

                                var field = mapServiceLayer && mapServiceLayer.fields ? array.filter(mapServiceLayer.fields,lang.hitch(this, function(x){
                                    return x.alias == k;
                                })) : null;
                                field = field && field.length > 0 ? field[0] : null;
                                if (field && (field.isHyperLink || field.hyperLinkType) && d.data[k]) {
                                    var linkType = field.hyperLinkType || 'http';

                                    if (linkType === 'network-file') {
                                        if(field.serverKey){
                                            domConstruct.create('a', {
                                                href: this.accessFileService + "?serverKey="+field.serverKey+"&fileName="+d.data[k],
                                                innerHTML:field.hyperLinkLabel || this.linksName,
                                                target: '_blank'
                                            }, domConstruct.create("td", null, rowWrapper));
                                        } else {
                                            domConstruct.create('a', {
                                                href: this.accessFileService + "?protocol="+field.protocol+"&url="+field.url + d.data[k],
                                                innerHTML: field.hyperLinkLabel || this.linksName,
                                                target: '_blank'
                                            }, domConstruct.create("td", null, rowWrapper));
                                        }
                                    } else {
                                        d.data[k] = this.addLinkProtocol(d.data[k], linkType);

                                        domConstruct.create("a", {
                                            href: d.data[k],
                                            innerHTML: field.hyperLinkLabel || this.linksName,
                                            target: '_blank'
                                        }, domConstruct.create("td", null, rowWrapper));
                                    }
                                }
                                else if ((this.replaceLinks && this.isLink(d.data[k])) || (service.fileProperties && service.fileProperties.indexOf(k)  > -1)) {
                                    if (service.fileProperties && service.fileProperties.indexOf(k) > -1) {
                                        d.data[k] = this.addLinkProtocol(d.data[k], 'file');
                                    }

                                    domConstruct.create("a", {
                                        href: d.data[k],
                                        innerHTML: this.linksName,
                                        target: '_blank'
                                    }, domConstruct.create("td", null, rowWrapper));
                                }
                                else if (this.replaceFiles && (
                                        (service.networkFileProperties && service.networkFileProperties.indexOf(k) > -1) || this.isNetworkFile(d.data[k])
                                    )) {
                                    domConstruct.create('a', {
                                        href: this.accessFileService + d.data[k],
                                        innerHTML: this.linksName,
                                        target: '_blank'
                                    }, domConstruct.create("td", null, rowWrapper));
                                }
                                else {
                                    domConstruct.create("td", { innerHTML: this.replaceNullsFunc(d.data[k]) }, rowWrapper);
                                }

                                ++cpt;
                            }
                        }

                        hasOneTable[service.serviceId + "-" + d.layerId] = true;
//                  panes[service.serviceId + "-" + d.layerId].set('open', true);
                    }));
                    if (this.removeThematicalLayerPaneIfNoData) {
                        array.forEach(Object.keys(panes), lang.hitch(this, function(panesId) {
                            if (panes[panesId].mustBeDestroy == null) {
                                domConstruct.empty(panes[panesId].domNode);
                            }
                        }))
                    }
                }
            },

            replaceNullsFunc: function(val) {
                if (!this.replaceNulls) {
                    return val;
                }

                if (val == null || (typeof(val) === 'string' && val.toLowerCase() === 'null')) {
                    val = '';
                }

                return val;
            }

        });
    });