diff --git a/conf/_install/dependency.xml b/conf/_install/dependency.xml index 14366ebb2ea9a48312ccc266f1e7a50413709305..43b51ea07363ab489a542d2d8967d8a7264dec44 100644 --- a/conf/_install/dependency.xml +++ b/conf/_install/dependency.xml @@ -5,32 +5,32 @@ <dependency> <nature>framework</nature> <name>vitis</name> - <version>app_vmap</version> + <version>next_app_vmap</version> </dependency> <dependency> <nature>modules</nature> <name>module_vmap</name> - <version>app_vmap</version> + <version>next_app_vmap</version> </dependency> <dependency> <nature>modules</nature> <name>module_vm4ms</name> - <version>app_vmap</version> + <version>next_app_vmap</version> </dependency> <dependency> <nature>modules</nature> <name>module_anc</name> - <version>app_vmap</version> + <version>next_app_vmap</version> </dependency> <dependency> <nature>modules</nature> <name>module_cadastreV2</name> - <version>app_vmap</version> + <version>next_app_vmap</version> </dependency> <dependency> <nature>modules</nature> <name>module_cadastre</name> - <version>app_vmap</version> + <version>next_app_vmap</version> </dependency> </dependenciesCollection> </installer> diff --git a/src/module_cadastre/.gitignore b/src/module_cadastre/.gitignore index 98ef169d65ec22973d313123ec3a178af98b7d71..d8b5d9919508b3efbd1b1fdc1d91adb22b53876d 100644 --- a/src/module_cadastre/.gitignore +++ b/src/module_cadastre/.gitignore @@ -1,2 +1,17 @@ -web_service/conf/properties* -web_service/conf/version.inc +client +vas +conf/closure +conf/node_modules/ +conf/properties.json +src/closure/conf/depswriter/ +src/vitis/vas/log/ +src/vitis/vas/public/ +src/vitis/vas/server/ +src/vitis/vas/ws_data/ +src/vitis/vas/tmp/ +src/vitis/client/modules/ +! src/vitis/client/modules/vitis/ +src/vitis/vas/rest/ws/* +! src/vitis/vas/rest/ws/vitis/ +src/vitis/vas/sql/* +! src/vitis/vas/sql/sqlQueries.xml diff --git a/src/module_vmap/module/css/vmap.less b/src/module_vmap/module/css/vmap.less index 0afd13f194d292e38f188753422b6b48c5ebab8c..cc42f401d348f812f18c9a25d00af7abcaa4dcb4 100644 --- a/src/module_vmap/module/css/vmap.less +++ b/src/module_vmap/module/css/vmap.less @@ -236,7 +236,7 @@ html, body { position: relative; height: 100%; } -app-map > div { +app-map > div, app-map-compare > div{ width: auto; height: 100%; background-color: @background; @@ -380,7 +380,7 @@ input[readonly] { display: -ms-flex !important; display: flex !important; } -#map-container{ +#map-container, #map-container-compare{ -webkit-transition: all 300ms ease-out 0s; -o-transition: all 300ms ease-out 0s; transition: all 300ms ease-out 0s; @@ -389,8 +389,37 @@ input[readonly] { height: ~"-webkit-calc(100% - 32px)"; height: ~"-o-calc(100% - 32px)"; height: ~"calc(100% - 32px)"; + width : 100%; } -#map-container.minus{ +#map-container.half,#map-container-compare.half{ + width : calc(50% ~"-" @right-sidebar-width/2); + float: left; +} +#map-container-compare.half{ + border-left: solid 2px #4a4a41; +} +/*#map-container.right-module-bar-present{ + width : calc(100% ~"-" @right-sidebar-width); +}*/ +/*#map-container.left-map-manager-open{ + width : calc(100% ~"-" @right-sidebar-width ~"-" @left-sidebar-content-width); +}*/ +#map-container.half.left-map-manager-open, #map-container-compare.half.left-map-manager-open{ + width : calc(50% ~"-" @right-sidebar-width/2 ~"-" @left-sidebar-content-width/2); +} +#map-container.half.right-module-bar-present,#map-container-compare.half.right-module-bar-present{ + width : calc(50% ~"-" @right-sidebar-width/2 ~"-" @left-sidebar-width/2); +} +#map-container.half.right-module-bar-present.left-map-manager-open,#map-container-compare.half.right-module-bar-present.left-map-manager-open{ + width : calc(50% ~"-" @right-sidebar-width/2 ~"-" @left-sidebar-width/2 ~"-" @left-sidebar-content-width/2); +} +#map-container.half.right-module-bar-present.right-module-manager-open,#map-container-compare.half.right-module-bar-present.right-module-manager-open{ + width : calc(50% ~"-" @right-sidebar-width/2 ~"-" @left-sidebar-width/2 ~"-" @right-sidebar-content-width/2); +} +#map-container.half.right-module-bar-present.left-map-manager-open.right-module-manager-open,#map-container-compare.half.right-module-bar-present.left-map-manager-open.right-module-manager-open{ + width : calc(50% ~"-" @right-sidebar-width/2 ~"-" @left-sidebar-width/2 ~"-" @left-sidebar-content-width/2 ~"-" @right-sidebar-content-width/2); +} +#map-container.minus,#map-container-compare.minus{ height: 95%; height: ~"-moz-calc(100% - 47px)"; height: ~"-webkit-calc(100% - 47px)"; @@ -399,13 +428,13 @@ input[readonly] { font-size: 12px; padding: 0px 0px; } -#map-container.open{ +#map-container.open, #map-container-compare.open{ height: -moz-calc(100% ~"-" @botom-open-height ~"-" 47px); height: -webkit-calc(100% ~"-" @botom-open-height ~"-" 47px); height: -o-calc(100% ~"-" @botom-open-height ~"-" 47px); height: calc(100% ~"-" @botom-open-height ~"-" 47px); } -#map-container.open2{ +#map-container.open2, #map-container-compare.open2{ height: -moz-calc(100% ~"-" @botom-open2-height ~"-" 47px); height: -webkit-calc(100% ~"-" @botom-open2-height ~"-" 47px); height: -o-calc(100% ~"-" @botom-open2-height ~"-" 47px); @@ -810,6 +839,35 @@ app-layertree button:hover { text-align: center; background-color: transparent; } + +.ol-target-overlay .ol-target +{ border: 1px solid transparent; + box-shadow: 0 0 1px 1px #fff; + display: block; + height: 20px; + width: 0; +} + +.ol-target-overlay .ol-target:after, +.ol-target-overlay .ol-target:before +{ content:""; + border: 1px solid #369; + box-shadow: 0 0 1px 1px #fff; + display: block; + width: 20px; + height: 0; + position:absolute; + top:9px; + left:-9px; +} +.ol-target-overlay .ol-target:after +{ box-shadow: none; + height: 20px; + width: 0; + top:0px; + left:0px; +} + #map-name, #current-projection{ position: initial; } @@ -2371,3 +2429,12 @@ div.vmap-select-scale-alert{ max-width: 197px !important; text-align: center !important; } + +#basic-tools-dropdown-comapremode{ + margin: -10px -1px; + width: 30%; + min-width: 450px; + max-width: 550px; + min-height: 55px; + padding-top: 15px !important; +} diff --git a/src/module_vmap/module/forms/vmap_business_object/vmap_business_object_vmap_business_object.js b/src/module_vmap/module/forms/vmap_business_object/vmap_business_object_vmap_business_object.js index ad663b75ea42b64cae3ef34ae7ed92a5700ea8f9..80ce27242794ab26e6305251870eb4adbaa0c17b 100644 --- a/src/module_vmap/module/forms/vmap_business_object/vmap_business_object_vmap_business_object.js +++ b/src/module_vmap/module/forms/vmap_business_object/vmap_business_object_vmap_business_object.js @@ -250,6 +250,21 @@ var oFormScope; oFormValues['id_field']['options'] = aColumnsOptions; } } + if (angular.isDefined(oFormValues['geom_column'])) { + if (angular.isDefined(oFormValues['geom_column']['options'])) { + oFormValues['geom_column']['options'] = aColumnsOptions; + } + } + if (angular.isDefined(oFormValues['search_field'])) { + if (angular.isDefined(oFormValues['search_field']['options'])) { + oFormValues['search_field']['options'] = aColumnsOptions; + } + } + if (angular.isDefined(oFormValues['result_field'])) { + if (angular.isDefined(oFormValues['result_field']['options'])) { + oFormValues['result_field']['options'] = aColumnsOptions; + } + } }); }, diff --git a/src/module_vmap/module/forms/vmap_business_object/vmap_business_object_vmap_business_object.json b/src/module_vmap/module/forms/vmap_business_object/vmap_business_object_vmap_business_object.json index b5697404c934a44fa2069f9ed2ce3be2fec2b480..17dbe0468ee4c3609c0710e359ad976f627aea44 100644 --- a/src/module_vmap/module/forms/vmap_business_object/vmap_business_object_vmap_business_object.json +++ b/src/module_vmap/module/forms/vmap_business_object/vmap_business_object_vmap_business_object.json @@ -291,41 +291,76 @@ }, { "fields": [{ - "type": "text", + "type": "editable_select", "name": "geom_column", "label": "FORM_GEOM_COLUMN_DEVELOPMENT_0", "required": true, - "pattern": "", - "nb_cols": 6, - "id": "New_el_10_12_1" + "nb_cols": 5 + }, { + "type": "button", + "class": "btn-group btn-group-sm margin-top-20", + "nb_cols": 1, + "buttons": [{ + "type": "button", + "name": "table-datalist", + "label": "FORM_GEOM_COLUMN_DEVELOPMENT_0", + "class": "btn-primary", + "event": "loadVMapBoFormColumns()", + "glyphicon": "refresh" + } + ] }] }, { "fields": [{ - "type": "text", + "type": "editable_select", "name": "search_field", "label": "FORM_SEARCH_FIELD_0", - "nb_cols": 6, - "id": "New_el_11_13_1", + "nb_cols": 5, "tooltip": { "title": "", "content": "FORM_SEARCH_FIELD_0_TOOLTIP", "container": "body" } + }, { + "type": "button", + "class": "btn-group btn-group-sm margin-top-20", + "nb_cols": 1, + "buttons": [{ + "type": "button", + "name": "table-datalist", + "label": "FORM_SEARCH_FIELD_0", + "class": "btn-primary", + "event": "loadVMapBoFormColumns()", + "glyphicon": "refresh" + } + ] }] }, { "fields": [{ - "type": "text", + "type": "editable_select", "name": "result_field", "label": "FORM_RESULT_FIELD_0", - "nb_cols": 6, - "id": "New_el_12_14_1", + "nb_cols": 5, "tooltip": { "title": "", "content": "FORM_RESULT_FIELD_0_TOOLTIP", "container": "body" } + }, { + "type": "button", + "class": "btn-group btn-group-sm margin-top-20", + "nb_cols": 1, + "buttons": [{ + "type": "button", + "name": "table-datalist", + "label": "FORM_RESULT_FIELD_0", + "class": "btn-primary", + "event": "loadVMapBoFormColumns()", + "glyphicon": "refresh" + } + ] }] }, { @@ -685,41 +720,76 @@ }, { "fields": [{ - "type": "text", + "type": "editable_select", "name": "geom_column", "label": "FORM_GEOM_COLUMN_DEVELOPMENT_0", "required": true, - "pattern": "", - "nb_cols": 6, - "id": "New_el_10_12_1" + "nb_cols": 5 + }, { + "type": "button", + "class": "btn-group btn-group-sm margin-top-20", + "nb_cols": 1, + "buttons": [{ + "type": "button", + "name": "table-datalist", + "label": "FORM_GEOM_COLUMN_DEVELOPMENT_0", + "class": "btn-primary", + "event": "loadVMapBoFormColumns()", + "glyphicon": "refresh" + } + ] }] }, { "fields": [{ - "type": "text", + "type": "editable_select", "name": "search_field", "label": "FORM_SEARCH_FIELD_0", - "nb_cols": 6, - "id": "New_el_11_13_1", + "nb_cols": 5, "tooltip": { "title": "", "content": "FORM_SEARCH_FIELD_0_TOOLTIP", "container": "body" } + }, { + "type": "button", + "class": "btn-group btn-group-sm margin-top-20", + "nb_cols": 1, + "buttons": [{ + "type": "button", + "name": "table-datalist", + "label": "FORM_SEARCH_FIELD_0", + "class": "btn-primary", + "event": "loadVMapBoFormColumns()", + "glyphicon": "refresh" + } + ] }] }, { "fields": [{ - "type": "text", + "type": "editable_select", "name": "result_field", "label": "FORM_RESULT_FIELD_0", - "nb_cols": 6, - "id": "New_el_12_14_1", + "nb_cols": 5, "tooltip": { "title": "", "content": "FORM_RESULT_FIELD_0_TOOLTIP", "container": "body" } + }, { + "type": "button", + "class": "btn-group btn-group-sm margin-top-20", + "nb_cols": 1, + "buttons": [{ + "type": "button", + "name": "table-datalist", + "label": "FORM_RESULT_FIELD_0", + "class": "btn-primary", + "event": "loadVMapBoFormColumns()", + "glyphicon": "refresh" + } + ] }] }, { diff --git a/src/module_vmap/module/javascript/app/vmap/map/map.js b/src/module_vmap/module/javascript/app/vmap/map/map.js index 7c0ba9a4a13165ccacc01ee5c7584bd9b561101d..fbd9fabb1a9b9305ce02faa83d8b38f4bfa9b227 100644 --- a/src/module_vmap/module/javascript/app/vmap/map/map.js +++ b/src/module_vmap/module/javascript/app/vmap/map/map.js @@ -389,6 +389,12 @@ nsVmap.Map = function () { if (oVmap['properties']['is_mobile']) { this_.trackGPSPosition(); } + + // Termine les dessins par le clic droit + this.oOpenLayersMap_.getViewport().addEventListener('contextmenu', function (evt) { + evt.preventDefault(); + this_.termineDrawInteractions(); + }) }; /** @@ -1209,6 +1215,29 @@ nsVmap.Map.prototype.trackGPSPosition = function () { } }; +/** + * Termine all the draw interactions + * + */ +nsVmap.Map.prototype.termineDrawInteractions = function () { + oVmap.log('nsVmap.Map.prototype.termineDrawInteractions'); + + for (var i = 0; i < this.vmapInteractions_.length; i++) { + if (this.vmapInteractions_[i] instanceof ol.interaction.Draw) { + try { + // Termine le dessin en cours + this.vmapInteractions_[i].finishDrawing(); + // Desactive la fonctionnalié pour ne pas commencer un autre dessin + this.vmapInteractions_[i].setActive(false); + // Réactive la fonctionnalité + setTimeout(angular.bind(this, function(oDrawInteraction){ + oDrawInteraction.setActive(true); + }, this.vmapInteractions_[i]), 500); + } catch (e) {} + } + } +}; + /******************************************** * INTERFACE MOBILE *******************************************/ diff --git a/src/module_vmap/module/javascript/app/vmap/map/mapcompare.js b/src/module_vmap/module/javascript/app/vmap/map/mapcompare.js new file mode 100644 index 0000000000000000000000000000000000000000..4fdf3a756d3a58291345c3b5b19ca7a9428f311a --- /dev/null +++ b/src/module_vmap/module/javascript/app/vmap/map/mapcompare.js @@ -0,0 +1,760 @@ +/* global nsVmap, ol, oVmap, goog, angular, vitisApp, bootbox */ + +/** + * @author: Anthony Borghi + * @Description: Fichier contenant la classe nsVmap.MapCompare + * cette classe permet l'initialisation de la carte + */ + +goog.provide('nsVmap.MapCompare'); + +goog.require('oVmap'); + +goog.require('ol.Map'); +goog.require('ol.View'); +goog.require('MapJSON'); +goog.require('ol.Overlay'); +goog.require('ol.source.Vector'); +goog.require('ol.layer.Vector'); +goog.require('goog.async.AnimationDelay'); + +/** + * @classdesc + * Class {@link nsVmap.MapCompare}: initializes the map to compare + * + * @constructor + * @export + */ +nsVmap.MapCompare = function () { + oVmap.log("nsVmap.MapCompare"); + + var this_ = this; + + /** + * Map layers + * @type {Array.<ol.layer>} + * @private + */ + this.olLayers_ = []; + + /** + * Map view + * @type {ol.View} + * @private + */ + this.olView_ = new ol.View({ + center: [0, 0], + zoom: 2 + }); + + /** + * Map + * @type {ol.map} + * @private + */ + this.oOpenLayersMap_ = new ol.Map({ + layers: this.olLayers_, + view: this.olView_, + moveTolerance: 5 + }); + + this.oOpenLayersMap_.getViewport().setAttribute('id', 'map1Compare'); + /** + * Contient les évènements ajoutés sur la carte par la méthode addEventOnMap ou setEventOnMap + * @type {array} + * @private + */ + this.vmapEvents_ = []; + + /** + * Contient les évènements ajoutés sur la carte par la méthode addDrawInteraction ou setDrawInteraction + * @type {array} + * @private + */ + this.vmapInteractions_ = []; + + /** + * Contient les tooltips ajoutés par addTooltip + * @type {array} + * @private + */ + this.vmapOverlays_ = []; + + /** + * Initialisé dans le controlleur + * @type {nsVmap.Map.MapTooltip} + * @private + */ + this.vmapTooltip_ = {}; + // Ajoute les couches à reprojeter en cas de changement de carte dans layersToTransform_ + this.layersToTransform_ = []; +} + +/** + * nsVmap.Map.oOpenLayersMap_ getter + * @return {ol.map} Used map + * @export + * @api experimental + */ +nsVmap.MapCompare.prototype.getOLMap = function () { + return this.oOpenLayersMap_; +}; + +/** + * nsVmap.Map.olView_ setter + * @param {ol.View} view View to use + * @export + * @api experimental + */ +nsVmap.MapCompare.prototype.setOpenLayersView = function (view) { + this.olView_ = view; + this.oOpenLayersMap_.setView(this.olView_); +}; + +/** + * Use this function to add a new vector layer + * @param {object} opt_options + * @param {object} opt_options.style + * @param {object} opt_options.extent + * @param {object} opt_options.minResolution + * @param {object} opt_options.maxResolution + * @param {object} opt_options.opacity + * @param {object} opt_options.properties + * @param {object} opt_options.visible + * @param {object} opt_options.zIndex + * @returns {undefined} + */ +nsVmap.MapCompare.prototype.addVectorLayer = function (opt_options) { + oVmap.log('nsVmap.MapCompare.prototype.addVectorLayer'); + + var vectorLayer = new ol.layer.Vector({ + map: this.oOpenLayersMap_, + source: new ol.source.Vector({ + useSpatialIndex: false + }), + updateWhileAnimating: true, + updateWhileInteracting: true + }); + + if (goog.isDef(opt_options)) { + if (goog.isDef(opt_options.style)) + vectorLayer.setStyle(opt_options.style); + + if (goog.isDef(opt_options.extent)) + vectorLayer.setExtent(opt_options.extent); + + if (goog.isDef(opt_options.minResolution)) + vectorLayer.setMinResolution(opt_options.minResolution); + + if (goog.isDef(opt_options.maxResolution)) + vectorLayer.setMaxResolution(opt_options.maxResolution); + + if (goog.isDef(opt_options.opacity)) + vectorLayer.setOpacity(opt_options.opacity); + + if (goog.isDef(opt_options.properties)) + vectorLayer.setProperties(opt_options.properties); + + if (goog.isDef(opt_options.visible)) + vectorLayer.setVisible(opt_options.visible); + + if (goog.isDef(opt_options.zIndex)) + vectorLayer.setZIndex(opt_options.zIndex); + } + + // Ajoute la couche à layersToTransform_ pour que les features soient reprojetés en cas de changement de projection + this.layersToTransform_.push(vectorLayer); + + return vectorLayer; +}; + +/** + * Remove events and interactions and then add a interaction + * @param {ol.interaction.Interaction} interaction + * @param {string|undefined} currentAction name of the current action + * @returns {ol.interaction.Interaction} + */ +nsVmap.MapCompare.prototype.setInteraction = function (interaction, currentAction) { + oVmap.log('nsVmap.MapCompare.prototype.setInteraction'); + // Supprime les anciens évènements et interractions + this.removeActionsOnMap(); + // Ajoute la nouvelle interaction + this.addInteraction(interaction); + // Définit l'action en cours + if (goog.isDef(currentAction)) + this.setCurrentAction(currentAction); + return interaction; +}; + +/** + * Add a interaction + * @param {ol.interaction.Interaction} interaction + * @param {string|undefined} currentAction name of the current action + * @returns {ol.interaction.Interaction} + */ +nsVmap.MapCompare.prototype.addInteraction = function (interaction, currentAction) { + oVmap.log('nsVmap.MapCompare.prototype.addInteraction'); + // Ajout de l'interaction + this.oOpenLayersMap_.addInteraction(interaction); + // Stocke l'interaction + this.vmapInteractions_.push(interaction); + // Définit l'action en cours + if (goog.isDef(currentAction)) + this.setCurrentAction(currentAction); + return interaction; +}; + +/** + * currentAction setter + * @param {string} currentAction + * @export + */ +nsVmap.MapCompare.prototype.setCurrentAction = function (currentAction) { + var scope = angular.element($("#map1Compare")).scope(); + scope.$evalAsync(function (scope) { + scope['ctrl']['currentAction'] = currentAction; + }); +}; + +/** + * Remove the mapTooltip and the actions added by addEventOnMap, setEventOnMap, addDrawInteraction or setDrawInteraction + * @returns {undefined} + * @export + */ +nsVmap.MapCompare.prototype.removeActionsAndTooltips = function () { + this.removeActionsOnMap(); + //this.getMapTooltip().hide(); + for (var i = 0; i < this.vmapOverlays_.length; i++) { + this.vmapOverlays_[i].getElement().style.display = "none"; + } +}; + +/** + * Remove the events and draw interactions added by addEventOnMap, setEventOnMap, addDrawInteraction or setDrawInteraction + * @returns {undefined} + * @export + */ +nsVmap.MapCompare.prototype.removeActionsOnMap = function () { + oVmap.log('nsVmap.Map.prototype.removeActionsOnMap'); + // Supprime les évènements + for (var i = 0; i < this.vmapEvents_.length; i++) { + ol.Observable.unByKey(this.vmapEvents_[i]); + } + + // Supprime les interractions + for (var i = 0; i < this.vmapInteractions_.length; i++) { + + // Supprime les features occasionelles + if (goog.isDef(this.vmapInteractions_[i].getFeatures)) + this.vmapInteractions_[i].getFeatures().clear(); + this.oOpenLayersMap_.removeInteraction(this.vmapInteractions_[i]); + } + + // Définit l'action en cours + this.setCurrentAction(''); +}; + +/** + * Set a event on the map and remove the others. + * @param {string|Array.<string>} type The event type or array of event types. + * @param {function(?): ?} listener The listener function. + * @param {Object=} opt_this The object to use as `this` in `listener`. + * @param {string|undefined} currentAction name of the current action + * @return {goog.events.Key} Unique key for the listener. + * @export + */ +nsVmap.MapCompare.prototype.setEventOnMap = function (type, listener, opt_this, currentAction) { + oVmap.log('nsVmap.Map.prototype.setEventOnMap'); + if (!goog.isDef(type)) { + console.error('setEventOnMap: type not defined'); + return 0; + } + + if (!goog.isDef(listener)) { + console.error('setEventOnMap: listener not defined'); + return 0; + } + + opt_this = goog.isDef(opt_this) ? opt_this : ''; + // Supprime les anciens évènements et interractions + this.removeActionsOnMap(); + // Ajoute le nouvel évènement + var event = this.addEventOnMap(type, listener, opt_this); + // Définit l'action en cours + if (goog.isDef(currentAction)) + this.setCurrentAction(currentAction); + return event; +}; + +/** + * Add a certain type of event on the map. + * @param {string|Array.<string>} type The event type or array of event types. + * @param {function(?): ?} listener The listener function. + * @param {Object=} opt_this The object to use as `this` in `listener`. + * @param {string|undefined} currentAction name of the current action + * @return {goog.events.Key} Unique key for the listener. + * @export + */ +nsVmap.MapCompare.prototype.addEventOnMap = function (type, listener, opt_this, currentAction) { + + if (!goog.isDef(type)) { + console.error('setEventOnMap: type not defined'); + return 0; + } + + if (!goog.isDef(listener)) { + console.error('setEventOnMap: listener not defined'); + return 0; + } + + opt_this = goog.isDef(opt_this) ? opt_this : ''; + // Active l'évènement + var event = this.oOpenLayersMap_.on(type, listener, opt_this); + // Stocke l'évènement + this.vmapEvents_.push(event); + // Définit l'action en cours + if (goog.isDef(currentAction)) + this.setCurrentAction(currentAction); + return event; +}; + +/** + * Get the current scale + * @param {object} opt_options + * @param {boolean|undefined} opt_options.pretty true for pretty format (ex: 1:25,000) + * @returns {Number|String} + * @export + */ +nsVmap.MapCompare.prototype.getScale = function (opt_options) { + oVmap.log('nsVmap.MapCompare.prototype.getScale'); + + opt_options = goog.isDef(opt_options) ? opt_options : {}; + opt_options['pretty'] = goog.isDef(opt_options['pretty']) ? opt_options['pretty'] : false; + + var wgs84Sphere_ = new ol.Sphere(6378137); + var projection = this.oOpenLayersMap_.getView().getProjection(); + + var map = oVmap.getMapCompare().getOLMap(); + + // récupère les coordonnées d'une ligue de 1cm (avec le zoom en cours) + var line = map.getView().calculateExtent([37.795275591, 0]); + var c1 = ol.proj.transform([line[0], line[1]], projection, 'EPSG:4326'); + var c2 = ol.proj.transform([line[2], line[3]], projection, 'EPSG:4326'); + + // Récuère la longueur sur la carte de la ligne de 1cm + var length = wgs84Sphere_.haversineDistance(c1, c2); + + // donc 1m sur la carte correspond à (length mètres dans la réalité x 100) + var scale = length * 100; + + // Rend l'échelle sous format (1:25,000) + if (opt_options['pretty'] === true) { + scale = this.getPrettyScale(scale); + } + + return scale; +}; + +/** + * Set the map scale + * @param {number} scale + * @returns {number} new scale + * @export + */ +nsVmap.MapCompare.prototype.setScale = function (scale) { + oVmap.log('nsVmap.Map.prototype.setScale'); + + // calcule et va à l'échelle celon une règle de 3 + var currentScale = this.getScale(); + var currentResolution = this.oOpenLayersMap_.getView().getResolution(); + + var scaleResolution = scale * currentResolution / currentScale; + this.oOpenLayersMap_.getView().setResolution(scaleResolution); + + // Ajuste l'échelle en augementant la résolution + currentScale = this.getScale(); + + oVmap.log(currentScale); +}; + +/** + * Get the scale like (1:25,000) + * @param {number} scale + * @returns {String} scale (pretty) + */ +nsVmap.MapCompare.prototype.getPrettyScale = function (scale) { + + // Rend l'échelle sous format (1:25,000) + scale = String(Math.round(scale)); + var j = 1; + for (var i = scale.length - 1; i > 0; i--) { + if (j % 3 === 0) + scale = scale.slice(0, i) + ',' + scale.slice(i + Math.abs(0)); + j++; + } + scale = '1:' + scale; + + return scale; +}; + +/** + * App-specific directive wrapping the ngeo map directive. The directive's + * controller has a property "map" including a reference to the OpenLayers + * map. + * + * @return {angular.Directive} The directive specs. + * @constructor + */ +nsVmap.MapCompare.prototype.mapCompareDirective = function () { + oVmap.log("nsVmap.MapCompare.prototype.mapCompareDirective"); + return { + restrict: 'E', + scope: { + 'map': '=appMap', + 'currentAction': '=appAction' + }, + controller: 'AppMapCompareController', + controllerAs: 'ctrl', + bindToController: true, + template: '<div id="olMapCompare"></div>' + }; +}; + +/** + * The application's main controller. + * @ngInject + * @constructor + */ +nsVmap.MapCompare.prototype.mapCompareController = function ($scope, $window, $element, $timeout) { + oVmap.log("nsVmap.MapCompare.prototype.mapController"); + var this_ = this; + + /** + * @private + */ + this.$scope_ = $scope; + + /** + * @type {object} + */ + this.element = $element; + + /** + * Animation duration + * @type Number + * @private + */ + this.duration = 1000; + + /** + * Timestamp of the last map center sync + */ + this.lastMapSyncCenter_ = 0; + + /** + * Timestamp of the last map compare center sync + */ + this.lastCompareMapSyncCenter_ = 0; + + /** + * Timestamp of the last map scale sync + */ + this.lastMapSyncScale_ = 0; + + /** + * Timestamp of the last map compare scale sync + */ + this.lastCompareMapSyncScale_ = 0; + + /** + * @type {ol.Map} + * @private + */ + this.map = this['map']; + /** + * @type {ol.Overlay} + * @private + */ + this.targetOverlay_ = null; + + /** + * Objet permettant de lancer des fonctions utiles + * pour parser la définition de la carte + * @type MapJSON + */ + var oMapJSON = new MapJSON({ + 'properties': oVmap['properties'] + }); + + var tileSize = [oVmap['properties']['vmap']['wmsTilesWidth'], oVmap['properties']['vmap']['wmsTilesHeight']]; + + /** + * Contains the tileloaderror and imageloaderror events + * @private + */ + this.loadErrorEventsContainer_ = []; + + this.map.setTarget('olMapCompare'); + + $scope.$on("mapCompareChanged", function(){ + // MAJ de la taille du composant + this_.map.setSize([document.getElementById('olMapCompare').offsetWidth, document.getElementById('olMapCompare').offsetHeight]); + if (this_.map.getLayers().getArray().length > 0) + this_.map.getLayers().clear(); + + var tree_ = oVmap.getMapManager().getCompareLayersTree(); + var olView_ = oMapJSON.getViewFromDef(tree_, { + 'size': this_.map.getSize(), + 'tileSize': tileSize + }); + + var olLayers_ = oMapJSON.getLayersFromDef(tree_, { + 'size': this_.map.getSize(), + 'tileSize': tileSize + }); + // Définit la vue de la carte + this_.addView(olView_); + // Définit les couches de la carte + for (var i = 0; i < olLayers_.length; i++) { + this_.addLayer(olLayers_[i]); + } + $timeout(function(){ + this_.synchronizeMap(); + }, 10); + + // Rafraichit l'échelle + setTimeout(function () { + this_.updateCompareScaleMap(); + }); + }) + + /** + * Update the map size with animation + * @type goog.async.AnimationDelay + */ + this.animationDelay = new goog.async.AnimationDelay( + function () { + this_.map.updateSize(); + this_.map.renderSync(); + if (goog.now() - start < this_.duration) { + this_.animationDelay.start(); + } + }, $window); + + /** + * Watch for resizing + */ + $scope.$watchCollection(function () { + return [this_.element.children()[0]['clientWidth'], this_.element.children()[0]['clientHeight']]; + }, function () { + this_.startAnimation(); + }); +}; + +// Définit les directives et controlleurs +oVmap.module.directive('appMapCompare', nsVmap.MapCompare.prototype.mapCompareDirective); +oVmap.module.controller('AppMapCompareController', nsVmap.MapCompare.prototype.mapCompareController); + +/** + * Update the map size with animation + * @returns {undefined} + * @export + */ +nsVmap.MapCompare.prototype.mapCompareController.prototype.startAnimation = function () { + oVmap.log('nsVmap.MapCompare.prototype.mapCompareController.prototype.startAnimation'); + start = goog.now(); + this.animationDelay.stop(); + this.animationDelay.start(); +}; + +/** + * Update the map size with animation + * @returns {undefined} + */ +nsVmap.MapCompare.prototype.mapCompareController.prototype.synchronizeMap = function () { + oVmap.log('nsVmap.MapCompare.prototype.mapCompareController.prototype.synchronizeMap'); + + var this_ = this; + + // Synchro Échelle + oVmap.getMap().getOLMap().getTargetElement().addEventListener('mouseenter', function(){ + oVmap.getMap().getOLMap().on("moveend", this_.updateCompareScaleMap, this_); + this_.map.un("moveend", this_.updateScaleMap, this_); + }); + this_.map.getTargetElement().addEventListener('mouseenter', function(){ + oVmap.getMap().getOLMap().un("moveend", this_.updateCompareScaleMap, this_); + this_.map.on("moveend", this_.updateScaleMap, this_); + }); + + // Synchro centre + oVmap.getMap().getOLMap().on("pointerdrag", this_.updateCenterCompareMap, this_); + this_.map.on("pointerdrag", this_.updateCenterMap, this_); + + // Synchro curseur sur l'autre carte + oVmap.getMap().getOLMap().on('pointermove', function(e){ + var coord = e.coordinate; + //si le composant existe sur l'autre composant on le supprime + if(angular.element(".over-map-compare.ol-target-overlay").length > 0){ + this_.targetOverlay_.setPosition(undefined); + this_.map.removeOverlay(this_.targetOverlay_); + this_.targetOverlay_ = undefined; + angular.element(".over-map-compare.ol-target-overlay").remove(); + } + // si le composant n'existe pas on le crée + if (!this_.targetOverlay_){ + var element = document.createElement("div"); + element.classList.add("ol-target"); + this_.targetOverlay_ = new ol.Overlay({ 'element': element }); + this_.targetOverlay_.setPositioning('center-center'); + this_.map.addOverlay(this_.targetOverlay_); + element.parentElement.classList.add("ol-target-overlay"); + element.parentElement.classList.add("over-map"); + // hack to render targetOverlay before positioning it + this_.targetOverlay_.setPosition([0,0]); + } + + var oldProjection = oVmap.getMap().getOLMap().getView().getProjection().getCode(); + var newProjection = this_.map.getView().getProjection().getCode(); + + var convertCoord = ol.proj.transform(coord, oldProjection, newProjection) + + this_.targetOverlay_.setPosition(convertCoord); + }); + this_.map.on('pointermove', function(e){ + var coord = e.coordinate; + //si le composant existe sur l'autre composant on le supprime + if(angular.element(".over-map.ol-target-overlay").length > 0){ + this_.targetOverlay_.setPosition(undefined); + oVmap.getMap().getOLMap().removeOverlay(this_.targetOverlay_); + this_.targetOverlay_ = undefined; + angular.element(".over-map-compare.ol-target-overlay").remove(); + } + // si le composant n'existe pas on le crée + if (!this_.targetOverlay_){ + var element = document.createElement("div"); + element.classList.add("ol-target"); + this_.targetOverlay_ = new ol.Overlay({ 'element': element }); + this_.targetOverlay_.setPositioning('center-center'); + oVmap.getMap().getOLMap().addOverlay(this_.targetOverlay_); + element.parentElement.classList.add("ol-target-overlay"); + element.parentElement.classList.add("over-map-compare"); + // hack to render targetOverlay before positioning it + this_.targetOverlay_.setPosition([0,0]); + } + + var oldProjection = this_.map.getView().getProjection().getCode(); + var newProjection = oVmap.getMap().getOLMap().getView().getProjection().getCode(); + + var convertCoord = ol.proj.transform(coord, oldProjection, newProjection) + + this_.targetOverlay_.setPosition(convertCoord); + }); +}; + +/** + * Update the map extent with animation + * @returns {undefined} + */ +nsVmap.MapCompare.prototype.mapCompareController.prototype.updateCompareScaleMap = function(e) { console.log('updateCompareScaleMap'); + var this_ = this + this_.updateCenterCompareMap(); + oVmap.getMapCompare().setScale(oVmap.getMap().getScale()); + + this.lastCompareMapSyncScale_ = Date.now(); +} + +/** + * Update the map extent with animation + * @returns {undefined} + */ +nsVmap.MapCompare.prototype.mapCompareController.prototype.updateScaleMap = function(e) { console.log('updateScaleMap'); + var this_ = this + this_.updateCenterMap(); + oVmap.getMap().setScale(oVmap.getMapCompare().getScale()); + + this.lastMapSyncScale_ = Date.now(); +} + +/** +* Update the map extent with animation +* @returns {undefined} +*/ +nsVmap.MapCompare.prototype.mapCompareController.prototype.updateCenterMap = function(e) { + + var this_ = this + // Récupère l'étendue de la carte principale + var oldCenter = this_.map.getView().getCenter(); + + // Récupère l'ancienne et la nouvelle projection + var newProjection = oVmap.getMap().getOLMap().getView().getProjection().getCode(); + var oldProjection = this_.map.getView().getProjection().getCode(); + + var newCenter = ol.proj.transform(oldCenter, oldProjection, newProjection); + oVmap.getMap().getOLMap().getView().setCenter(newCenter); + + this.lastMapSyncCenter_ = Date.now(); +} + +/** +* Update the map extent with animation +* @returns {undefined} +*/ +nsVmap.MapCompare.prototype.mapCompareController.prototype.updateCenterCompareMap = function(e) { + + var this_ = this; + // Récupère l'étendue de la carte principale + var oldCenter = oVmap.getMap().getOLMap().getView().getCenter(); + + // Récupère l'ancienne et la nouvelle projection + var oldProjection = oVmap.getMap().getOLMap().getView().getProjection().getCode(); + var newProjection = this_.map.getView().getProjection().getCode(); + + var newCenter = ol.proj.transform(oldCenter, oldProjection, newProjection); + this_['map'].getView().setCenter(newCenter); + + this.lastCompareMapSyncCenter_ = Date.now(); +} + +/** + * Add a layer on the map + * @param {object} olLayer + */ +nsVmap.MapCompare.prototype.mapCompareController.prototype.addLayer = function (olLayer) { + oVmap.log('nsVmap.MapCompare.prototype.mapCompareController.prototype.addLayer'); + this['map'].addLayer(olLayer); +}; + +/** + * Add the olView + * @param {object} olView + * @returns {undefined} + */ +nsVmap.MapCompare.prototype.mapCompareController.prototype.addView = function (olView) { + oVmap.log('nsVmap.nsMapManager.LayersTree.prototype.LayertreeController.prototype.addView'); + + // Récupère l'étendue de la carte principale + var oldExtent = oVmap.getMap().getOLMap().getView().calculateExtent(this['map'].getSize()); + + // Récupère l'ancienne et la nouvelle projection + var oldProjection = oVmap.getMap().getOLMap().getView().getProjection().getCode(); + var newProjection = olView.getProjection().getCode(); + + // Set le home position pour cette vue + olView.set('homePosition', { + center: olView.getCenter(), + resolution: olView.getResolution() + }); + + oVmap.getMapCompare().setOpenLayersView(olView); + this['map'].setView(olView); + this['proj'] = olView.getProjection().getCode(); + + // Reprojette en cas de changment de carte + if (goog.isDef(oldProjection) && goog.isDef(newProjection) && goog.isDef(oldExtent) /*&& goog.isDef(oldPosition)*/) { + // Reprojette l'étendue + var newExtent = ol.proj.transformExtent(oldExtent, oldProjection, newProjection); + this['map'].getView().fit(newExtent, { + nearest: true + }); + } +}; diff --git a/src/module_vmap/module/javascript/app/vmap/mapmanager/mapmanager.js b/src/module_vmap/module/javascript/app/vmap/mapmanager/mapmanager.js index c13c9aae888788c3844528a192df7f652b71cb9a..13114d60d7874701fa6fc84a16d079e020ee1634 100644 --- a/src/module_vmap/module/javascript/app/vmap/mapmanager/mapmanager.js +++ b/src/module_vmap/module/javascript/app/vmap/mapmanager/mapmanager.js @@ -45,6 +45,12 @@ nsVmap.nsMapManager.MapManager = function () { * @private */ this.oLayersTree_ = {}; + /** + * Object which contains the layers tree + * @type {object} + * @private + */ + this.oCompareLayersTree_ = {}; /** * Objet which contains the map modal manager tool @@ -281,20 +287,73 @@ nsVmap.nsMapManager.MapManager.prototype.loadMap = function (element) { }); }; +/** + * Load a new map to compare + * @param {object} element Html element witch contains the url to the map.json file + * @param {object} element.url link to the map.json file + * @export + */ +nsVmap.nsMapManager.MapManager.prototype.loadCompareMap = function (element) { + oVmap.log('nsVmap.nsMapManager.MapManager.loadCompareMap'); + + if (oVmap['properties']['is_mobile']) { + oVmap.getToolsManager().getBasicTools().hideMobileMenu(); + } + + // Récupère l'url + var sUrl = element.getAttribute("url"); + + if (!goog.isDefAndNotNull(sUrl)) { + return 0; + } + if (sUrl.length === 0) { + return 0; + } + + // Récupère l'arbre de couches + var this_ = this; + this_.getAjaxLayersTree(sUrl, function(oTree){ + + oVmap.log("oTree: ", oTree); + + // Change la variable oLayersTree + this_.setCompareLayersTree(oTree); + + // Rafraichit la carte + this_.reloadMap(); + + // Signale que c'est la carte utilisée + for (var i = 0; i < this_.oMapCatalog_['maps'].length; i++) { + if (this_.oMapCatalog_['maps'][i]['url'] === sUrl) + this_.oMapCatalog_['compareMap'] = i; + } + this_.setUsedMap('compare'); + + oVmap.log("oVmap.event: mapCompareChanged"); + oVmap['scope'].$broadcast('mapCompareChanged'); + angular.element('#map-compare-tool-btn').click(); + setTimeout(function () { + oVmap.resizeLayerTools(); + }, 1000); + }); +}; + /** * Put the used map to used * @returns {undefined} */ -nsVmap.nsMapManager.MapManager.prototype.setUsedMap = function () { +nsVmap.nsMapManager.MapManager.prototype.setUsedMap = function (sKey) { oVmap.log('nsVmap.nsMapManager.MapManager.prototype.setUsedMap'); + sKey = (goog.isDefAndNotNull(sKey)) ? sKey : 'used'; + // Met toutes les cartes à used = false for (var i = 0; i < this.oMapCatalog_['maps'].length; i++) { - this.oMapCatalog_['maps'][i]['used'] = false; + this.oMapCatalog_['maps'][i][sKey] = false; } // Met la carte utilisée à used = true - this.oMapCatalog_['maps'][this.oMapCatalog_['usedMap']]['used'] = true; + this.oMapCatalog_['maps'][this.oMapCatalog_[sKey + 'Map']][sKey] = true; oVmap.resizeLayerTools(false); }; @@ -1206,16 +1265,59 @@ nsVmap.nsMapManager.MapManager.prototype.getLayersTree = function () { return this.oLayersTree_; }; +/** + * LayersTree_ getter (also set the visibility of the layers with the new ones) + * @return {object} Layers tree + * @api experimental + * @export + */ +nsVmap.nsMapManager.MapManager.prototype.getCompareLayersTree = function () { + + var oMap = oVmap.getMapCompare().getOLMap(); + var aLayers = oMap.getLayers().getArray(); + + /** + * Recursive function that update parameters recursively + * @param {object} node + */ + var updateOnTree = function (node) { + // Recursive + if (goog.isDef(node['children'])) { + for (var i = 0; i < node['children'].length; i++) { + updateOnTree(node['children'][i]); + } + } + // Update + if (goog.isDef(node['olLayer'])) { + node['visible'] = node['olLayer'].getVisible(); + node['index'] = aLayers.indexOf(node['olLayer']); + node['opacity'] = node['olLayer'].getOpacity(); + } + }; + + for (var i = 0; i < this.oCompareLayersTree_['children'].length; i++) { + updateOnTree(this.oCompareLayersTree_['children'][i]); + } + + return this.oCompareLayersTree_; +}; + /** * Get the JSON layers tree * @returns {String} * @export */ -nsVmap.nsMapManager.MapManager.prototype.getJSONLayersTree = function () { +nsVmap.nsMapManager.MapManager.prototype.getJSONLayersTree = function ($bCompareLayersTree) { // recupère une copie de l'arbre des couches var oLayersTree = jQuery.extend(true, {}, oVmap.getMapManager().getLayersTree()); var oMap = oVmap.getMap().getOLMap(); + + if($bCompareLayersTree){ + oLayersTree = jQuery.extend(true, {}, oVmap.getMapManager().getCompareLayersTree()); + oMap = oVmap.getMapCompare().getOLMap(); + } + var aDiscardedAttributes = [ 'olLayer', '$$hashKey', @@ -1281,6 +1383,15 @@ nsVmap.nsMapManager.MapManager.prototype.getJSONLayersTree = function () { nsVmap.nsMapManager.MapManager.prototype.setLayersTree = function (oTree) { this.oLayersTree_ = oTree; }; +/** + * LayersTree_ setter + * @param {object} oTree Layers tree + * @api experimental + * @export + */ +nsVmap.nsMapManager.MapManager.prototype.setCompareLayersTree = function (oTree) { + this.oCompareLayersTree_ = oTree; +}; /** * oMapCatalog_ getter diff --git a/src/module_vmap/module/javascript/app/vmap/mapmanager/mapmodal/maplistlitle.js b/src/module_vmap/module/javascript/app/vmap/mapmanager/mapmodal/maplistlitle.js index bd1150b4f386c2807fa30a27b3638aeeb84a8c26..0782d0c2dc9c6cb82acca40e873c11c7c2ec3bb9 100644 --- a/src/module_vmap/module/javascript/app/vmap/mapmanager/mapmodal/maplistlitle.js +++ b/src/module_vmap/module/javascript/app/vmap/mapmanager/mapmodal/maplistlitle.js @@ -42,7 +42,11 @@ nsVmap.nsMapManager.nsMapModal.MapListLitle.prototype.maplistlitleDirective = fu controller: 'AppMaplistlitleController', controllerAs: 'ctrl', bindToController: true, - templateUrl: oVmap['properties']['vmap_folder'] + '/' + 'template/layers/mapmodal/' + (oVmap['properties']['is_mobile'] ? 'maplistlitle_mobile.html' : 'maplistlitle.html') + templateUrl: oVmap['properties']['vmap_folder'] + '/' + 'template/layers/mapmodal/' + (oVmap['properties']['is_mobile'] ? 'maplistlitle_mobile.html' : 'maplistlitle.html'), + link : function ($scope, $element, $attrs){ + $scope["compare"] = goog.isDefAndNotNull($attrs["compare"]); + $attrs.$observe("compare", function(){$scope["compare"] = goog.isDefAndNotNull($attrs["compare"])}); + } }; }; diff --git a/src/module_vmap/module/javascript/app/vmap/requires.js b/src/module_vmap/module/javascript/app/vmap/requires.js index 2eae1b6a727b42ff523d7e606e3dfa5baecbe4fd..997cb30e697bb1d836e3591af4d3f28eb68c81c6 100755 --- a/src/module_vmap/module/javascript/app/vmap/requires.js +++ b/src/module_vmap/module/javascript/app/vmap/requires.js @@ -8,7 +8,8 @@ goog.provide('vmap'); goog.require('oVmap'); goog.require('nsVmap.Map'); +goog.require('nsVmap.MapCompare'); goog.require('nsVmap.Map.MapTooltip'); goog.require('nsVmap.Map.MapPopup'); goog.require('nsVmap.nsMapManager.MapManager'); -goog.require('nsVmap.nsToolsManager.ToolsManager'); \ No newline at end of file +goog.require('nsVmap.nsToolsManager.ToolsManager'); diff --git a/src/module_vmap/module/javascript/app/vmap/tools/basictools.js b/src/module_vmap/module/javascript/app/vmap/tools/basictools.js index f53955c43cccd66024db099c860b32b003b11aca..32d672545e8e07809eef979e646647a798855dd1 100644 --- a/src/module_vmap/module/javascript/app/vmap/tools/basictools.js +++ b/src/module_vmap/module/javascript/app/vmap/tools/basictools.js @@ -17,6 +17,7 @@ goog.require('nsVmap.nsToolsManager.Select'); goog.require('nsVmap.nsToolsManager.Insert'); goog.require('nsVmap.nsToolsManager.Print'); goog.require('nsVmap.nsToolsManager.Urlexporter'); +goog.require('nsVmap.nsToolsManager.Compare'); /** @@ -429,4 +430,4 @@ nsVmap.nsToolsManager.BasicTools.prototype.basictoolsController.prototype.locati // Définit la directive et le controller oVmap.module.directive('appBasictools', nsVmap.nsToolsManager.BasicTools.prototype.basictoolsDirective); -oVmap.module.controller('AppBasictoolsController', nsVmap.nsToolsManager.BasicTools.prototype.basictoolsController); \ No newline at end of file +oVmap.module.controller('AppBasictoolsController', nsVmap.nsToolsManager.BasicTools.prototype.basictoolsController); diff --git a/src/module_vmap/module/javascript/app/vmap/tools/compare.js b/src/module_vmap/module/javascript/app/vmap/tools/compare.js new file mode 100644 index 0000000000000000000000000000000000000000..076766831e9746bc36e12cac715b641048b9b8ed --- /dev/null +++ b/src/module_vmap/module/javascript/app/vmap/tools/compare.js @@ -0,0 +1,81 @@ +/* global oVmap, nsVmap, goog, ol, vitisApp */ + +/** + * @author: Anthony Borghi + * @Description: Fichier contenant la classe nsVmap.nsToolsManager.Urlexporter + * cette classe permet à l'utilisateur d'exporter une url pour un autre utilisateur + */ +goog.provide('nsVmap.nsToolsManager.Compare'); + +goog.require('oVmap'); + +/** + * @classdesc + * Class {@link nsVmap.nsToolsManager.VmapUser} + * @constructor + * @export + */ +nsVmap.nsToolsManager.compare = function () { + oVmap.log('nsVmap.nsToolsManager.Compare'); +}; + + + +/** + * Directive + * @return {angular.Directive} The directive specs. + * @constructor + */ +nsVmap.nsToolsManager.compare.prototype.compareDirective = function () { + oVmap.log("nsVmap.nsToolsManager.compare.prototype.compareDirective"); + return { + restrict: 'A', + scope: { + 'map': '=appMap', + 'lang': '=appLang' + }, + controller: 'AppCompareMode', + controllerAs: 'ctrl', + bindToController: true, + templateUrl: oVmap['properties']['vmap_folder'] + '/' + 'template/tools/comparemapmanager.html' + }; +}; + +/** + * Controler + * @constructor + * @param {object} $scope + * @returns {undefined} + * @ngInject + */ +nsVmap.nsToolsManager.compare.prototype.compareController = function ($scope, $element) { + oVmap.log("nsVmap.nsToolsManager.compare.prototype.compareController"); + + var this_ = this; + + this.$scope_ = $scope; + + /** + * The current properties + */ + this['properties'] = oVmap['properties']; + + /** + * The current token + */ + this['token'] = oVmap['properties']['token']; + + /** + * @type {boolean} + */ + this["useCompareMode"] = false; + + $scope.$watch("ctrl.useCompareMode", function(){ + $scope.$root["compare_enabled"] = this_["useCompareMode"]; + }) + +}; + +// Définit la directive et le controller +oVmap.module.directive('appCompareMode', nsVmap.nsToolsManager.compare.prototype.compareDirective); +oVmap.module.controller('AppCompareMode', nsVmap.nsToolsManager.compare.prototype.compareController); diff --git a/src/module_vmap/module/javascript/app/vmap/tools/infocontainer.js b/src/module_vmap/module/javascript/app/vmap/tools/infocontainer.js index e04b0496471f34d663bfaed78a3dfe88d0e20ac2..e499814f2fbb84c8edcb52ff224fbab69d70bd8a 100644 --- a/src/module_vmap/module/javascript/app/vmap/tools/infocontainer.js +++ b/src/module_vmap/module/javascript/app/vmap/tools/infocontainer.js @@ -662,6 +662,7 @@ nsVmap.nsToolsManager.InfoContainer.prototype.infocontainerController.prototype. $("#opener-bottombar").css("visibility", "visible"); } $("#map-container").addClass('minus'); + $("#map-container-compare").addClass('minus'); // Ouvre la barre this.$timeout(function () { diff --git a/src/module_vmap/module/javascript/app/vmap/tools/insert.js b/src/module_vmap/module/javascript/app/vmap/tools/insert.js index 803d13add3e95a2916e129c4eb60e6db3b981b01..456136bce313f4f78931835bdeec5e500dec4500 100644 --- a/src/module_vmap/module/javascript/app/vmap/tools/insert.js +++ b/src/module_vmap/module/javascript/app/vmap/tools/insert.js @@ -187,6 +187,7 @@ nsVmap.nsToolsManager.Insert.prototype.inserttoolController = function ($scope, this['snapOptions']['mode'] = oVmap['properties']['snapping']['defaut_snapp_mode']; this['snapOptions']['limit'] = oVmap['properties']['snapping']['defaut_limit']; this['snapOptions']['visible'] = oVmap['properties']['snapping']['defaut_visibility']; + this['snapOptions']['avoidSuperpositions'] = {}; } /** @@ -257,6 +258,11 @@ nsVmap.nsToolsManager.Insert.prototype.inserttoolController = function ($scope, */ $scope['aQueryableBOs'] = oVmap.getMapManager().getQueryableBusinessObjectsAsArray(true); + /** + * Business objects avaliable for avoiding superpositions + */ + $scope['aAvoidSuperpositionsBOs'] = []; + /** * Object to insert * oInsertObject.sFormDefinitionName name of the form (insert, upload, display) @@ -366,8 +372,10 @@ nsVmap.nsToolsManager.Insert.prototype.inserttoolController = function ($scope, // Au changement d'objet métier en cours d'insertion this.$scope_.$watch('selectedBoId', function () { - this_.updateInsertForm(); - this_.selectCurrentBoForSnapping(); + this_.updateInsertForm(null, function(){ + this_.selectCurrentBoForSnapping(); + this_.loadAvoidSuperpositionBos(); + }); }); // Affiche les modales en plein écran pour la version mobile @@ -411,6 +419,7 @@ nsVmap.nsToolsManager.Insert.prototype.inserttoolController.prototype.loadInsert }); this.checkEditionScale(); + this.loadAvoidSuperpositionBos(); }; /** @@ -433,6 +442,40 @@ nsVmap.nsToolsManager.Insert.prototype.inserttoolController.prototype.selectCurr this.checkEditionScale(); }; + +/** + * Load this.aAvoidSuperpositionsBOs + * + */ +nsVmap.nsToolsManager.Insert.prototype.inserttoolController.prototype.loadAvoidSuperpositionBos = function () { + oVmap.log('nsVmap.nsToolsManager.Insert.inserttoolController.loadAvoidSuperpositionBos'); + + var this_ = this; + + // Types de géométries pour le calcul des jointures + var aActiveGeomTypes = ['POLYGON', 'MULTIPOLYGON', 'GEOMETRY', 'GEOMETRYCOLLECTION']; + + // Objets métiers actifs pour la calcul des jointures + this.$scope_['aAvoidSuperpositionsBOs'] = []; + + if (goog.isDefAndNotNull(this.$scope_['oInsertObject']['sGeomType'])) { + + // Si la couche en cours d'insertion est dans aActiveGeomTypes + if (aActiveGeomTypes.indexOf(this.$scope_['oInsertObject']['sGeomType']) !== -1) { + for (var i = 0; i < this_.$scope_['aQueryableBOs'].length; i++) { + + // Si la couche cible est dans aActiveGeomTypes + if (goog.isDefAndNotNull(this_.$scope_['aQueryableBOs'][i]['bo_geom_type'])) { + if(aActiveGeomTypes.indexOf(this_.$scope_['aQueryableBOs'][i]['bo_geom_type']) !== -1){ + + this.$scope_['aAvoidSuperpositionsBOs'].push(this_.$scope_['aQueryableBOs'][i]); + } + } + } + } + } +} + /** * Vérifie que l'échelle en cours respecte les spécification de l'objet métier */ @@ -1068,9 +1111,11 @@ nsVmap.nsToolsManager.Insert.prototype.inserttoolController.prototype.startDrawi var this_ = this; this.draw_.on('drawend', function (evt) { - // Si la géométrie est un cercle, alors elle est remplacée par un polygone à 32 côtés var feature = evt.feature; + // Si la géométrie est un cercle, alors elle est remplacée par un polygone à 32 côtés feature = this_.updateCircleGeoms(feature); + // Évite les superpositions avec les autres couches si besoin + this_.avoidSuperpositions(feature); }, this); @@ -1141,6 +1186,118 @@ nsVmap.nsToolsManager.Insert.prototype.inserttoolController.prototype.updateCirc return feature; }; +/** + * Edit the given feature to avoid superpositions with layers defined in snapOptions.avoidSuperpositions + * @param {ol.Feature} olFeature + * @returns {ol.Feature} + */ +nsVmap.nsToolsManager.Insert.prototype.inserttoolController.prototype.avoidSuperpositions = function (olFeature) { + oVmap.log('nsVmap.nsToolsManager.Insert.inserttoolController.avoidSuperpositions'); + + // Objets métiers à intersecter + var aSuperpositionBos = []; + for (var bo_id in this['snapOptions']['avoidSuperpositions']) { + if (this['snapOptions']['avoidSuperpositions'][bo_id] === true) { + aSuperpositionBos.push(bo_id); + } + } + + // Remplace la géométrie par celle calculée + if (aSuperpositionBos.length > 0) { + this.setDiffGeom_(aSuperpositionBos, olFeature) + } +} + +/** + * Modify the feature geometry to avoid superpositions with BOs in aSuperpositionBos + * + * @param {string} aSuperpositionBos + * @param {ol.Feature} olFeature + * @param {object|undefines} opt_options + */ +nsVmap.nsToolsManager.Insert.prototype.inserttoolController.prototype.setDiffGeom_ = function (aSuperpositionBos, olFeature, opt_options) { + oVmap.log('nsVmap.nsToolsManager.Insert.inserttoolController.setDiffGeom_'); + + if (!goog.isArray(aSuperpositionBos)) { + return 0; + } + if (!goog.isDefAndNotNull(olFeature)) { + return 0; + } + if (!goog.isDefAndNotNull(opt_options)) { + opt_options = { + bo_index: 0 + } + } + + var this_ = this; + var sEWKTGeom = oVmap.getEWKTFromGeom(olFeature.getGeometry()); + + this.getDiffGeom_(aSuperpositionBos[opt_options.bo_index], sEWKTGeom).then(function(sNewEWKTGeom){ + + // Remplace la géométrie + olFeature.setGeometry(oVmap.getGeomFromEWKT(sNewEWKTGeom)); + + // Relance la fonction pour les autres objets métiers + opt_options.bo_index ++; + if (opt_options.bo_index < aSuperpositionBos.length) { + this_.setDiffGeom_(aSuperpositionBos, olFeature, opt_options); + } + }, function(err){ + console.error('Cannot get the diff geom: ', err) + }); + +} + +/** + * Get the diff superposition geometry + * + * @param {string} sBoId + * @param {string} sEWKTGeom + * @return {promise} + */ +nsVmap.nsToolsManager.Insert.prototype.inserttoolController.prototype.getDiffGeom_ = function (sBoId, sEWKTGeom) { + oVmap.log('nsVmap.nsToolsManager.Insert.inserttoolController.getDiffGeom_'); + + var deferred = this.$q_.defer(); + ajaxRequest({ + 'method': 'POST', + 'url': oVmap['properties']['api_url'] + '/vmap/querys/' + sBoId + '/diff_geometry', + 'headers': { + 'X-HTTP-Method-Override': 'GET', + 'Accept': 'application/x-vm-json' + }, + 'data': { + 'intersect_geom': sEWKTGeom + }, + 'scope': this.$scope_, + 'success': function (response) { + + if (!goog.isDefAndNotNull(response['data'])) { + deferred.reject('response.data not defined'); + return 0; + } + if (goog.isDefAndNotNull(response['data']['errorMessage'])) { + deferred.reject(response['data']['errorMessage']); + return 0; + } + if (!goog.isDefAndNotNull(response['data'][0])) { + deferred.reject('response.data[0] not defined'); + return 0; + } + if (!goog.isDefAndNotNull(response['data'][0]['diff_geom'])) { + deferred.reject('response.data[0].diff_geom not defined'); + return 0; + } + deferred.resolve(response['data'][0]['diff_geom']); + }, + 'error': function (response) { + deferred.reject(response); + } + }); + return deferred.promise; +} + /** * Update feature for scope.oInsertObject */ @@ -1478,7 +1635,17 @@ nsVmap.nsToolsManager.Insert.prototype.inserttoolController.prototype.getMobileB nsVmap.nsToolsManager.Insert.prototype.inserttoolController.prototype.showSnappingOptionsModal = function () { oVmap.log('nsVmap.nsToolsManager.Insert.prototype.inserttoolController.prototype.showSnappingOptionsModal'); + var this_ = this; this['tmpSnapOptions'] = angular.copy(this['snapOptions']); + + this.$scope_.$applyAsync(function(){ + for (var i = 0; i < this_.$scope_['aQueryableBOs'].length; i++) { + if (!goog.isDefAndNotNull(this_['tmpSnapOptions']['avoidSuperpositions'][this_.$scope_['aQueryableBOs'][i]['bo_id']])) { + this_['tmpSnapOptions']['avoidSuperpositions'][this_.$scope_['aQueryableBOs'][i]['bo_id']] = false; + } + } + }); + $('#vmap-insert-snap-options-modal').modal('show'); }; @@ -1597,6 +1764,10 @@ nsVmap.nsToolsManager.Insert.prototype.inserttoolController.prototype.loadBoVect oBo['bo_snapping_loaded'] = null; return 0; } + if (!goog.isDefAndNotNull(response['data'][0])) { + oBo['bo_snapping_loaded'] = null; + return 0; + } if (response['data'][0]['count'] > this_['snapOptions']['snappingObjectsLimit']) { oBo['bo_snapping_loaded'] = null; var text = 'Limit de points atteinte pour object '; @@ -1609,7 +1780,8 @@ nsVmap.nsToolsManager.Insert.prototype.inserttoolController.prototype.loadBoVect if (goog.isDefAndNotNull(response['data'][i]['geom'])) { geom = response['data'][i]['geom']; aFeatures.push(new ol.Feature({ - geometry: oVmap.getGeomFromEWKT(geom) + geometry: oVmap.getGeomFromEWKT(geom), + 'bo_id': bo_id })); } } diff --git a/src/module_vmap/module/javascript/app/vmap/tools/print.js b/src/module_vmap/module/javascript/app/vmap/tools/print.js index 8c779787a04216d8ac5ca2ec60d40e2b2bd29a12..efc99e6add1af7135b89c9210efd195df339902c 100644 --- a/src/module_vmap/module/javascript/app/vmap/tools/print.js +++ b/src/module_vmap/module/javascript/app/vmap/tools/print.js @@ -103,6 +103,9 @@ nsVmap.nsToolsManager.Print.prototype.printController = function ($timeout, $com */ $scope['modelIndex'] = 0; + $scope["managePrintZoneInProgress"] = false; + $scope["manageComparePrintZoneInProgress"] = false; + /** * @public */ @@ -173,7 +176,12 @@ nsVmap.nsToolsManager.Print.prototype.printController = function ($timeout, $com * The print box object * @private */ - this.printBox_ = new nsVmap.nsToolsManager.PrintBox(); + this.printBox_ = new nsVmap.nsToolsManager.PrintBox({'map_object':oVmap.getMap()}); + /** + * The print box object + * @private + */ + this.printBoxCompare_ = new nsVmap.nsToolsManager.PrintBox({'map_object':oVmap.getMapCompare()}); // mise à jour de l'échelle dans le forulaire d'impression lors d'un mouvement sur la carte this.listenScaleChanges(); @@ -197,6 +205,9 @@ nsVmap.nsToolsManager.Print.prototype.printController = function ($timeout, $com oVmap['scope'].$on('toggleOutTools', function () { if (!$('#print-select-btn').hasClass('active')) { this_.printBox_.hide(); + this_.printBoxCompare_.hide(); + $scope["managePrintZoneInProgress"] = false; + $scope["manageComparePrintZoneInProgress"] = false; } }); }; @@ -352,7 +363,10 @@ nsVmap.nsToolsManager.Print.prototype.printController.prototype.loadModelParmas2 oVmap.log('nsVmap.nsToolsManager.Print.printController.loadModelParmas2'); // Récupère la taille de la carte this.printedMapSize_ ainsi que le coefficient this.resizeCoeff_ - this.setPrintedMapSize(this.template_); + oPrintMapSize = this.getPrintedMapSize(this.template_); + + this.printedMapSize_ = oPrintMapSize.printedMapSize; + this.resizeCoeff_ = oPrintMapSize.resizeCoeff; // Pré-rempli le champ "Résolution" this['resolution'] = this.resizeCoeff_; @@ -364,6 +378,23 @@ nsVmap.nsToolsManager.Print.prototype.printController.prototype.loadModelParmas2 this.printBox_.setSize(this.printedMapSize_); this.printBox_.show(); + if(this.$scope_["$root"]["compare_enabled"]){ + this.oComparePrintMapSize = this.getPrintedMapSize(this.template_,"#map1Compare","#map_image_compare"); + if(this.oComparePrintMapSize !== 0){ + // Pré-rempli le champ "Résolution" + this['resolutionCompare'] = this.oComparePrintMapSize.resizeCoeff; + + // Ajuste l'échelle avec le niveau de détail + this['currentScaleCompare'] = oVmap.getMapCompare().getPrettyScale(oVmap.getMapCompare().getScale() / this.oComparePrintMapSize.resizeCoeff); + + // Dessine un carré d'impression à chaque mouvement de la carte + this.printBoxCompare_.setSize(this.oComparePrintMapSize.printedMapSize); + this.printBoxCompare_.show(); + } else { + this.printBoxCompare_.hide(); + } + } + }; /** @@ -398,17 +429,24 @@ nsVmap.nsToolsManager.Print.prototype.printController.prototype.setTemplate = fu }; /** - * Set this.printedMapSize_ and this.resizeCoeff_ - * @param {object} template + * Get the print map size and resolution coeff + * + * @param {type} template + * @param {type} sElementMapId + * @param {type} sPrintId + * @return {object} */ -nsVmap.nsToolsManager.Print.prototype.printController.prototype.setPrintedMapSize = function (template) { - oVmap.log('nsVmap.nsToolsManager.Print.printController.setPrintedMapSize'); +nsVmap.nsToolsManager.Print.prototype.printController.prototype.getPrintedMapSize = function (template, sElementMapId, sPrintId) { + oVmap.log('nsVmap.nsToolsManager.Print.printController.getPrintedMapSize'); - var imageDiv = $(template).find('#map_image'); + sPrintId = (goog.isDefAndNotNull(sPrintId)) ? sPrintId : '#map_image'; + sElementMapId = (goog.isDefAndNotNull(sElementMapId)) ? sElementMapId : '#map1'; + + var imageDiv = $(template).find(sPrintId); // Vérifie la présence de '#map_image' if (!goog.isDef(imageDiv.get(0))) { - console.error('Aucune balise #map_image trouvée dans le template'); + console.error('Aucune balise ' + sPrintId + ' trouvée dans le template'); return 0; } @@ -423,16 +461,19 @@ nsVmap.nsToolsManager.Print.prototype.printController.prototype.setPrintedMapSiz $(template).remove(); // Vérifie si la taille de la carte est suppérieur à la taille de l'écran - this.resizeCoeff_ = 1; + var resizeCoeff = 1; var tmpWidth = angular.copy(mapWidth); var tmpHeight = angular.copy(mapHeight); - while (mapWidth > ($('#map1').width()) || mapHeight > ($('#map1').height())) { - this.resizeCoeff_++; - mapWidth = tmpWidth / this.resizeCoeff_; - mapHeight = tmpHeight / this.resizeCoeff_; + while (mapWidth > ($(sElementMapId).width()) || mapHeight > ($(sElementMapId).height())) { + resizeCoeff++; + mapWidth = tmpWidth / resizeCoeff; + mapHeight = tmpHeight / resizeCoeff; } - this.printedMapSize_ = [mapWidth, mapHeight]; + return { + printedMapSize: [mapWidth, mapHeight], + resizeCoeff: resizeCoeff + } }; /** @@ -469,13 +510,32 @@ nsVmap.nsToolsManager.Print.prototype.printController.prototype.changeScale = fu nsVmap.nsToolsManager.Print.prototype.printController.prototype.managePrintZone = function () { oVmap.log('nsVmap.nsToolsManager.Print.prototype.printController.prototype.managePrintZone'); - if (this['currentAction'] === 'print-modifyPrintZone') { + if (this['currentAction'] === 'print-modifyPrintZone' && this.$scope_['managePrintZoneInProgress']) { this.printBox_.unmanagePrintBox(); + this.$scope_["managePrintZoneInProgress"] = false; } else { + this.$scope_["managePrintZoneInProgress"] = true; this.printBox_.managePrintBox('print-modifyPrintZone'); } }; +/** + * Detach the printZone from the view and allow to translate it + * @export + */ +nsVmap.nsToolsManager.Print.prototype.printController.prototype.manageComparePrintZone = function () { + oVmap.log('nsVmap.nsToolsManager.Print.prototype.printController.prototype.manageComparePrintZone'); + + if (this['currentAction'] === 'print-modifyPrintZone' && this.$scope_["manageComparePrintZoneInProgress"]) { + this.printBoxCompare_.unmanagePrintBox(); + this.$scope_["manageComparePrintZoneInProgress"] = false; + } else { + //this.printBox_.unmanagePrintBox(); + this.$scope_["manageComparePrintZoneInProgress"] = true; + this.printBoxCompare_.managePrintBox('print-modifyPrintZone'); + } +}; + /** * Prepare the print params and launch it * @returns {undefined} @@ -504,15 +564,28 @@ nsVmap.nsToolsManager.Print.prototype.printController.prototype.prepareAndLaunch var aPopupOverlayFeatures = oVmap.getMap().getPopupOverlayFeatures().getArray(); var aSelectionOverlayFeatures = oVmap.getMap().getSelectionOverlayFeatures().getArray(); - // Lance l'impression - var returnPrint = this.print({ + var oPrintOptions = { scope: scope, extent: extent, templateId: templateId, printStyleId: this.$scope_['selectedPrintstyleId'], resolutionCoeff: this['dpi'], features: goog.array.concat(aLocationOverlayFeatures, aPopupOverlayFeatures, aSelectionOverlayFeatures) - }); + }; + + // récupération des infos pour la carte de comparaison si le mode comparaison est actif + if(this.$scope_['$root']["compare_enabled"]){ + if(this.oComparePrintMapSize !== 0){ + // Enregistre l'échelle actuelle + this.currentScaleCompare_ = oVmap.getMapCompare().getScale({ + 'pretty': true + }); + oPrintOptions.extentCompare = this.printBoxCompare_.getExtent(); + } + } + + // Lance l'impression + var returnPrint = this.print(oPrintOptions); if (returnPrint === 1) { // Ferme l'outil d'impression @@ -618,9 +691,10 @@ nsVmap.nsToolsManager.Print.prototype.printController.prototype.print = function template.innerHTML = response['data']['data'][0]['definition']; var mapImageSize = this_.getTemplateTargetSize(template, '#map_image'); + var mapImageSizeCompare = this_.getTemplateTargetSize(template, '#map_image_compare'); var overviewSize = this_.getTemplateTargetSize(template, '#map_overview'); - var mapsJson = this_.getMapsJsonDef({ + var oJsonDefOptions = { mapId: opt_options.mapId, resolutionCoeff: opt_options.resolutionCoeff, extent: opt_options.extent, @@ -628,7 +702,15 @@ nsVmap.nsToolsManager.Print.prototype.printController.prototype.print = function featuresZoom: opt_options.featuresZoom, mapImageSize: mapImageSize, overviewSize: overviewSize - }) + } + + if(goog.isDefAndNotNull(opt_options.extentCompare)){ + oJsonDefOptions.extentCompare = opt_options.extentCompare; + oJsonDefOptions.mapIdCompare = opt_options.mapIdCompare; + oJsonDefOptions.mapImageSizeCompare = mapImageSizeCompare; + } + + var mapsJson = this_.getMapsJsonDef(oJsonDefOptions); // Récupère les infos de l'utilisateur this_.getUserInfos_().then(function (oUserInfos) { @@ -707,11 +789,18 @@ nsVmap.nsToolsManager.Print.prototype.printController.prototype.getMapsJsonDef = // mapId/mapJson var sMapId; var sMapJSON; + var sMapIdCompare; + var sMapJSONCompare; if (goog.isDefAndNotNull(opt_options.mapId)) { sMapId = opt_options.mapId; } else { sMapJSON = oVmap.getMapManager().getJSONLayersTree(); } + if (goog.isDefAndNotNull(opt_options.mapIdCompare)) { + sMapIdCompare = opt_options.mapIdCompare; + } else if (this.$scope_['$root']["compare_enabled"]) { + sMapJSONCompare = oVmap.getMapManager().getJSONLayersTree(true); + } // Extent var aExtent = goog.isDefAndNotNull(opt_options.extent) ? opt_options.extent : []; @@ -723,13 +812,16 @@ nsVmap.nsToolsManager.Print.prototype.printController.prototype.getMapsJsonDef = aExtent[3] + (aExtent[3] - aExtent[1]) ]; var sOverviewExtent = ''; + var sCompareExtent = ''; for (var i = 0; i < aExtent.length; i++) { if (i > 0) { sExtent += '|'; sOverviewExtent += '|'; + sCompareExtent += (goog.isDefAndNotNull(opt_options.extentCompare)) ? '|' : ''; } sExtent += aExtent[i]; sOverviewExtent += aOverviewExtent[i]; + sCompareExtent += (goog.isDefAndNotNull(opt_options.extentCompare)) ? opt_options.extentCompare[i] : ''; } // Features @@ -771,6 +863,15 @@ nsVmap.nsToolsManager.Print.prototype.printController.prototype.getMapsJsonDef = 'features_zoom': 400 }; } + if (goog.isDefAndNotNull(opt_options.mapImageSizeCompare) && this.$scope_.$root["compare_enabled"]) { + var oCompareDef = { + 'map_id': sMapIdCompare, + 'map_json': sMapJSONCompare, + 'image_size': (opt_options.mapImageSizeCompare[0] * resolutionCoeff) + '|' + (opt_options.mapImageSizeCompare[1] * resolutionCoeff), + 'resolution_coeff': resolutionCoeff, + 'extent': sCompareExtent + }; + } var oMapsJson = []; if (goog.isDefAndNotNull(oMapDef)) { @@ -786,6 +887,13 @@ nsVmap.nsToolsManager.Print.prototype.printController.prototype.getMapsJsonDef = }); } + if (goog.isDefAndNotNull(oCompareDef)) { + oMapsJson.push({ + 'target': '#map_image_compare', + 'map_definition': oCompareDef + }); + } + var mapsJson = JSON.stringify(oMapsJson); return mapsJson; diff --git a/src/module_vmap/module/javascript/app/vmap/tools/printBox.js b/src/module_vmap/module/javascript/app/vmap/tools/printBox.js index b359736577fd4fc861e58c471cf2f0aad568d5ae..d25f47f7a8ca5d9588d23e08f23767f1ad9d6c16 100755 --- a/src/module_vmap/module/javascript/app/vmap/tools/printBox.js +++ b/src/module_vmap/module/javascript/app/vmap/tools/printBox.js @@ -18,11 +18,13 @@ goog.require('ol.interaction.Translate'); nsVmap.nsToolsManager.PrintBox = function (opt_options) { oVmap.log('nsVmap.nsToolsManager.PrintBox'); - this.map_ = oVmap.getMap().getOLMap(); - // Valeurs par défaut opt_options = goog.isDefAndNotNull(opt_options) ? opt_options : {}; + this.oMap_ = (goog.isDefAndNotNull(opt_options["map_object"])? opt_options["map_object"]: oVmap.getMap()); + + this.map_ = this.oMap_.getOLMap(); + /** * The print box feature * @private @@ -45,7 +47,7 @@ nsVmap.nsToolsManager.PrintBox = function (opt_options) { * @type {ol.layer.Vector} * @private */ - this.oOpenLayersOverlay_ = oVmap.getMap().addVectorLayer(); + this.oOpenLayersOverlay_ = this.oMap_.addVectorLayer(); /** * @type {ol.Collection} @@ -110,7 +112,7 @@ nsVmap.nsToolsManager.PrintBox.prototype.managePrintBox = function (sInteraction this.unlistenMapMovements(); // Ajoute l'interaction de déplacement de la printBox - oVmap.getMap().setInteraction(this.translateInteraction_, sInteractionName); + this.oMap_.setInteraction(this.translateInteraction_, sInteractionName); }; @@ -122,12 +124,23 @@ nsVmap.nsToolsManager.PrintBox.prototype.unmanagePrintBox = function () { oVmap.log('nsVmap.nsToolsManager.PrintBox.unmanagePrintBox'); // remove l'action de modification - oVmap.getMap().removeActionsAndTooltips(); + this.oMap_.removeActionsAndTooltips(); this.drawPrintBox(); this.listenMapMovements(); }; +/** + * Cancel the printZone manage interaction and adapt the view on it + * @export + */ +nsVmap.nsToolsManager.PrintBox.prototype.unmanagePrintBoxAndLock = function () { + oVmap.log('nsVmap.nsToolsManager.PrintBox.unmanagePrintBox'); + + // remove l'action de modification + this.oMap_.removeActionsAndTooltips(); +}; + /** * Get the print box scale * @returns {Number|String} @@ -149,7 +162,7 @@ nsVmap.nsToolsManager.PrintBox.prototype.getScale = function () { nearest: true }); - var scale = oVmap.getMap().getScale(); + var scale = this.oMap_.getScale(); setTimeout(function () { // Retrouve la position initiale @@ -166,13 +179,13 @@ nsVmap.nsToolsManager.PrintBox.prototype.getScale = function () { * @export */ nsVmap.nsToolsManager.PrintBox.prototype.setScale = function (newScale) { - + // Échelle courante var currentScale = this.getScale(); // Calcul du delta entre l'échelle courrante et l'échelle voulue var deltaScale = newScale / currentScale; - + // Mise sous forme de variables pour une meilleure compréhension var currentExtent = this.getExtent(); var xmin = currentExtent[0]; @@ -185,7 +198,7 @@ nsVmap.nsToolsManager.PrintBox.prototype.setScale = function (newScale) { // Calcul de la nouvelle hauteur/largeur de la printBox var newLength = length * deltaScale; var newHeight = height * deltaScale; - + // Calcul des nouvelles coordonnées en fonction du centre et des nouvelles hauteur/largeur var center = this.printBoxFeature_.getGeometry().getInteriorPoint().getCoordinates(); var newXmin = center[0] - newLength / 2; @@ -198,10 +211,10 @@ nsVmap.nsToolsManager.PrintBox.prototype.setScale = function (newScale) { this.printBoxFeature_ = new ol.Feature({ geometry: box }); - + // Supprime l'ancienne feature this.oOpenLayersOverlayFeatures_.clear(); - + // Ajoute la nouvelle feature this.oOpenLayersOverlay_.getSource().addFeature(this.printBoxFeature_); }; @@ -239,7 +252,7 @@ nsVmap.nsToolsManager.PrintBox.prototype.getExtent = function () { */ nsVmap.nsToolsManager.PrintBox.prototype.listenMapMovements = function () { - this.printBoxEvent_ = oVmap.getMap().setEventOnMap('precompose', this.drawPrintBox, this); + this.printBoxEvent_ = this.oMap_.setEventOnMap('precompose', this.drawPrintBox, this); }; /** @@ -286,10 +299,12 @@ nsVmap.nsToolsManager.PrintBox.prototype.createPrintBox = function (printBoxSize var boxWidth = printBoxSize[0]; var boxHeight = printBoxSize[1]; - var x1 = $('#map1').width() / 2 - boxWidth / 2; - var x2 = $('#map1').width() / 2 + boxWidth / 2; - var y1 = $('#map1').height() / 2 - boxHeight / 2; - var y2 = $('#map1').height() / 2 + boxHeight / 2; + var sMapComponentId = this.map_.getViewport().getAttribute('id'); + + var x1 = $('#' + sMapComponentId).width() / 2 - boxWidth / 2; + var x2 = $('#' + sMapComponentId).width() / 2 + boxWidth / 2; + var y1 = $('#' + sMapComponentId).height() / 2 - boxHeight / 2; + var y2 = $('#' + sMapComponentId).height() / 2 + boxHeight / 2; var point1 = [x1, y2]; var point3 = [x2, y1]; @@ -306,4 +321,4 @@ nsVmap.nsToolsManager.PrintBox.prototype.createPrintBox = function (printBoxSize boxFeature.set('pixelExtent', [x1, y1, x2, y2]); return boxFeature; -}; \ No newline at end of file +}; diff --git a/src/module_vmap/module/javascript/app/vmap/tools/select/select.js b/src/module_vmap/module/javascript/app/vmap/tools/select/select.js index 6a7eddf0e1b15822a8732b90e569e4e05093d0fd..9c89bc22cbe78198752e73c76846568ace3d2d68 100755 --- a/src/module_vmap/module/javascript/app/vmap/tools/select/select.js +++ b/src/module_vmap/module/javascript/app/vmap/tools/select/select.js @@ -366,6 +366,7 @@ nsVmap.nsToolsManager.Select.prototype.selectController = function ($scope, $tim this['snapOptions']['mode'] = oVmap['properties']['snapping']['defaut_snapp_mode']; this['snapOptions']['limit'] = oVmap['properties']['snapping']['defaut_limit']; this['snapOptions']['visible'] = oVmap['properties']['snapping']['defaut_visibility']; + this['snapOptions']['avoidSuperpositions'] = {}; } /** @@ -373,6 +374,16 @@ nsVmap.nsToolsManager.Select.prototype.selectController = function ($scope, $tim */ this['tmpSnapOptions'] = angular.copy(this['snapOptions']); + /** + * Queryable Business Objects + */ + this['aQueryableBOs'] = []; + + /** + * Business objects avaliable for avoiding superpositions + */ + $scope['aAvoidSuperpositionsBOs'] = []; + /** * Tree resulting the various GetFeatureInfo requests */ @@ -523,10 +534,31 @@ nsVmap.nsToolsManager.Select.prototype.selectController = function ($scope, $tim features: this.oOverlayFeatures_ }); - this.modify_.on('modifyend', function () { + this.modify_.on('modifyend', function (evt) { + + // Récupère la feature ajoutée + var aFeatures = evt.features.getArray(); + + // Évite les superpositions avec les autres couches si besoin + var j = 0; + for (var i = 0; i < aFeatures.length; i++) { + this_.avoidSuperpositions(aFeatures[i]).then(function(){ + j++; + if (!j < aFeatures.length) { + setTimeout(function () { + this_.putFeaturesOnTheElement(this_.oOverlayFeatures_.getArray()); + }); + } + }); + } + + // Cas où avoidSuperpositions n'ait pas effectué de callback setTimeout(function () { - this_.putFeaturesOnTheElement(this_.oOverlayFeatures_.getArray()); - }); + if (j === 0) { + console.error('avoidSuperpositions never sents callback'); + this_.putFeaturesOnTheElement(this_.oOverlayFeatures_.getArray()); + } + }, 3000); }); /** @@ -685,6 +717,39 @@ nsVmap.nsToolsManager.Select.prototype.selectController.prototype.loadQueryableB }); }; +/** + * Load this.aAvoidSuperpositionsBOs + * + */ +nsVmap.nsToolsManager.Select.prototype.selectController.prototype.loadAvoidSuperpositionBos = function () { + oVmap.log('nsVmap.nsToolsManager.Select.selectController.loadAvoidSuperpositionBos'); + + var this_ = this; + + // Types de géométries pour le calcul des jointures + var aActiveGeomTypes = ['POLYGON', 'MULTIPOLYGON', 'GEOMETRY', 'GEOMETRYCOLLECTION']; + + // Objets métiers actifs pour la calcul des jointures + this.$scope_['aAvoidSuperpositionsBOs'] = []; + + if (goog.isDefAndNotNull(this['editableFeatureType'])) { + + // Si la couche en cours d'insertion est dans aActiveGeomTypes + if (aActiveGeomTypes.indexOf(this['editableFeatureType']) !== -1) { + for (var i = 0; i < this['aQueryableBOs'].length; i++) { + + // Si la couche cible est dans aActiveGeomTypes + if (goog.isDefAndNotNull(this['aQueryableBOs'][i]['bo_geom_type'])) { + if(aActiveGeomTypes.indexOf(this['aQueryableBOs'][i]['bo_geom_type']) !== -1){ + + this.$scope_['aAvoidSuperpositionsBOs'].push(this['aQueryableBOs'][i]); + } + } + } + } + } +} + /** * Vérifie que l'échelle en cours respecte les spécification de l'objet métier */ @@ -1880,6 +1945,9 @@ nsVmap.nsToolsManager.Select.prototype.selectController.prototype.editFeature = // Affiche la palette de modification $('#basictools-select-modify-palette').show(); + // Chage le liste des BO intersectables par calcul de polygones jointifs + this_.loadAvoidSuperpositionBos(); + // Timeout car lors du toggleOutTools, clearOverlays est lancé setTimeout(function () { // Ajoute la/les feature(s) @@ -2126,12 +2194,160 @@ nsVmap.nsToolsManager.Select.prototype.selectController.prototype.startDrawing = this_.oOverlayLayer_.getSource().addFeature(feature); } + // Évite les superpositions avec les autres couches si besoin + this_.avoidSuperpositions(feature); + // Ajoute les géométries en mode multi ou simple à editableSelection.olFeature this_.putFeaturesOnTheElement(this_.oOverlayFeatures_.getArray()); }); }, this); }; +/** + * Edit the given feature to avoid superpositions with layers defined in snapOptions.avoidSuperpositions + * @param {ol.Feature} olFeature + * @returns {ol.Feature} + */ +nsVmap.nsToolsManager.Select.prototype.selectController.prototype.avoidSuperpositions = function (olFeature) { + oVmap.log('nsVmap.nsToolsManager.Select.selectController.avoidSuperpositions'); + + var deferred = this.$q_.defer(); + + // Objets métiers à intersecter + var aSuperpositionBos = []; + for (var bo_id in this['snapOptions']['avoidSuperpositions']) { + if (this['snapOptions']['avoidSuperpositions'][bo_id] === true) { + aSuperpositionBos.push(bo_id); + } + } + + // Remplace la géométrie par celle calculée + if (aSuperpositionBos.length > 0) { + this.setDiffGeom_(aSuperpositionBos, olFeature).then(function(olFeature){ + deferred.resolve(olFeature); + }); + } else { + deferred.resolve(olFeature); + } + + return deferred.promise; +} + +/** + * Modify the feature geometry to avoid superpositions with BOs in aSuperpositionBos + * + * @param {string} aSuperpositionBos + * @param {ol.Feature} olFeature + * @param {object|undefines} opt_options + */ +nsVmap.nsToolsManager.Select.prototype.selectController.prototype.setDiffGeom_ = function (aSuperpositionBos, olFeature, opt_options) { + oVmap.log('nsVmap.nsToolsManager.Select.selectController.setDiffGeom_'); + + if (!goog.isArray(aSuperpositionBos)) { + return 0; + } + if (!goog.isDefAndNotNull(olFeature)) { + return 0; + } + if (!goog.isDefAndNotNull(opt_options)) { + opt_options = { + bo_index: 0 + } + } + + var this_ = this; + var deferred = this.$q_.defer(); + var sEWKTGeom = oVmap.getEWKTFromGeom(olFeature.getGeometry()); + + this.getDiffGeom_(aSuperpositionBos[opt_options.bo_index], sEWKTGeom).then(function(sNewEWKTGeom){ + + // Remplace la géométrie + olFeature.setGeometry(oVmap.getGeomFromEWKT(sNewEWKTGeom)); + + // Relance la fonction pour les autres objets métiers + opt_options.bo_index ++; + if (opt_options.bo_index < aSuperpositionBos.length) { + this_.setDiffGeom_(aSuperpositionBos, olFeature, opt_options).then(function(){ + deferred.resolve(olFeature); + }, function(error){ + console.error(error); + }); + } else { + deferred.resolve(olFeature); + } + }, function(err){ + console.error('Cannot get the diff geom: ', err) + }); + + return deferred.promise; +} + +/** + * Get the diff superposition geometry + * + * @param {string} sBoId + * @param {string} sEWKTGeom + * @return {promise} + */ +nsVmap.nsToolsManager.Select.prototype.selectController.prototype.getDiffGeom_ = function (sBoId, sEWKTGeom) { + oVmap.log('nsVmap.nsToolsManager.Select.selectController.getDiffGeom_'); + + var oParams = { + 'intersect_geom': sEWKTGeom + }; + + // Filtre pour ne pas s'éviter lui même + if (goog.isDefAndNotNull(this['editableSelection'])) { + if (this['editableSelection']['bo_type'] === sBoId) { + if (goog.isDefAndNotNull(this['editableSelection']['bo_id_field']) && + goog.isDefAndNotNull(this['editableSelection']['bo_id_value'])) { + + oParams['filter'] = { + 'column': this['editableSelection']['bo_id_field'], + 'compare_operator': '!=', + 'value': this['editableSelection']['bo_id_value'] + } + } + } + } + + var deferred = this.$q_.defer(); + ajaxRequest({ + 'method': 'POST', + 'url': oVmap['properties']['api_url'] + '/vmap/querys/' + sBoId + '/diff_geometry', + 'headers': { + 'X-HTTP-Method-Override': 'GET', + 'Accept': 'application/x-vm-json' + }, + 'data': oParams, + 'scope': this.$scope_, + 'success': function (response) { + + if (!goog.isDefAndNotNull(response['data'])) { + deferred.reject('response.data not defined'); + return 0; + } + if (goog.isDefAndNotNull(response['data']['errorMessage'])) { + deferred.reject(response['data']['errorMessage']); + return 0; + } + if (!goog.isDefAndNotNull(response['data'][0])) { + deferred.reject('response.data[0] not defined'); + return 0; + } + if (!goog.isDefAndNotNull(response['data'][0]['diff_geom'])) { + deferred.reject('response.data[0].diff_geom not defined'); + return 0; + } + deferred.resolve(response['data'][0]['diff_geom']); + }, + 'error': function (response) { + deferred.reject(response); + } + }); + return deferred.promise; +} + /** * Put the array of features passed on aFeatures on editableSelection.olFeature with MULTI... form * @param {array} aFeatures @@ -2363,7 +2579,17 @@ nsVmap.nsToolsManager.Select.prototype.selectController.prototype.finishEdition nsVmap.nsToolsManager.Select.prototype.selectController.prototype.showSnappingOptionsModal = function () { oVmap.log('nsVmap.nsToolsManager.Select.prototype.selectController.prototype.showSnappingOptionsModal'); + var this_ = this; this['tmpSnapOptions'] = angular.copy(this['snapOptions']); + + this.$scope_.$applyAsync(function(){ + for (var i = 0; i < this_['aQueryableBOs'].length; i++) { + if (!goog.isDefAndNotNull(this_['tmpSnapOptions']['avoidSuperpositions'][this_['aQueryableBOs'][i]['bo_id']])) { + this_['tmpSnapOptions']['avoidSuperpositions'][this_['aQueryableBOs'][i]['bo_id']] = false; + } + } + }); + $('#vmap-select-snap-options-modal').modal('show'); }; @@ -2477,6 +2703,10 @@ nsVmap.nsToolsManager.Select.prototype.selectController.prototype.loadBoVectorSn oBo['bo_snapping_loaded'] = null; return 0; } + if (!goog.isDefAndNotNull(response['data'][0])) { + oBo['bo_snapping_loaded'] = null; + return 0; + } if (response['data'][0]['count'] > this_['snapOptions']['snappingObjectsLimit']) { oBo['bo_snapping_loaded'] = null; var text = 'Limit de points atteinte pour object '; @@ -2489,7 +2719,8 @@ nsVmap.nsToolsManager.Select.prototype.selectController.prototype.loadBoVectorSn if (goog.isDefAndNotNull(response['data'][i]['geom'])) { geom = response['data'][i]['geom']; aFeatures.push(new ol.Feature({ - geometry: oVmap.getGeomFromEWKT(geom) + geometry: oVmap.getGeomFromEWKT(geom), + 'bo_id': bo_id })); } } diff --git a/src/module_vmap/module/javascript/app/vmap/tools/toolsmanager.js b/src/module_vmap/module/javascript/app/vmap/tools/toolsmanager.js index ba4c644aea4d99f191adc967b8a5f8d78f45a29a..1b6a247c6b746f13abf5c4fa6ff32e759973f169 100755 --- a/src/module_vmap/module/javascript/app/vmap/tools/toolsmanager.js +++ b/src/module_vmap/module/javascript/app/vmap/tools/toolsmanager.js @@ -143,13 +143,18 @@ nsVmap.nsToolsManager.ToolsManager.prototype.vmapToolsContainerDirective = funct /** * Basic tools Controller + * @param {object} $scope * @export + * @ngInject * @constructor */ -nsVmap.nsToolsManager.ToolsManager.prototype.vmapToolsController = function () { +nsVmap.nsToolsManager.ToolsManager.prototype.vmapToolsController = function ($scope) { oVmap.log("nsVmap.nsToolsManager.BasicTools.prototype.vmapToolsController"); this['oToolsTree'] = oVmap.getToolsManager().getToolsTree(); + + $scope.$root["bLoadVmapModule"] = goog.isDefAndNotNull(this['oToolsTree']); + this['openedTool'] = '_'; }; @@ -176,7 +181,7 @@ nsVmap.nsToolsManager.ToolsManager.prototype.loadSyncToolsTree = function () { oToolsTree = data['usermodules']; } }); - + return oToolsTree; }; @@ -225,4 +230,4 @@ nsVmap.nsToolsManager.ToolsManager.prototype.getTool = function (tool) { // Définit la directive et le controller oVmap.module.directive('appVmaptools', nsVmap.nsToolsManager.ToolsManager.prototype.vmapToolsDirective); oVmap.module.directive('toolsContainer', nsVmap.nsToolsManager.ToolsManager.prototype.vmapToolsContainerDirective); -oVmap.module.controller('AppVmaptoolsController', nsVmap.nsToolsManager.ToolsManager.prototype.vmapToolsController); \ No newline at end of file +oVmap.module.controller('AppVmaptoolsController', nsVmap.nsToolsManager.ToolsManager.prototype.vmapToolsController); diff --git a/src/module_vmap/module/javascript/app/vmap/tools/urlexporter.js b/src/module_vmap/module/javascript/app/vmap/tools/urlexporter.js index 85e757f8f70c2bac1538b099482fd06940cec290..d89684f26f381a40125ee0d52a88f24eaa559637 100644 --- a/src/module_vmap/module/javascript/app/vmap/tools/urlexporter.js +++ b/src/module_vmap/module/javascript/app/vmap/tools/urlexporter.js @@ -76,16 +76,6 @@ nsVmap.nsToolsManager.Urlexporter.prototype.urlExporterController = function ($s this["urlConstructor"](); - // Affiche les modales en plein écran pour la version mobile - //if (oVmap['properties']['is_mobile']) { - // $element.find('.modal').on('shown.bs.modal', function () { - // $('.modal-backdrop.fade.in').hide(); - // $('.modal.fade.in').find('.modal-dialog').addClass('mobile-full-modal'); - // }); - //} - - console.log(this['properties']); - // recalcule l'url quand on change de carte oVmap['scope'].$on('mapChanged', function () { this_["urlConstructor"](); @@ -135,6 +125,27 @@ nsVmap.nsToolsManager.Urlexporter.prototype.urlExporterController.prototype.urlC this["urlToExport"] = sUrl; }; + +/** + * Copy the generated URL on the clipboard + * + * @export + */ +nsVmap.nsToolsManager.Urlexporter.prototype.urlExporterController.prototype.copyUrl = function () { + oVmap.log("nsVmap.nsToolsManager.Urlexporter.urlExporterController.copyUrl"); + + /* Get the text field */ + var copyText = document.getElementById("urlExporterField"); + + /* Select the text field */ + copyText.select(); + + /* Copy the text inside the text field */ + document.execCommand("copy"); + + $.notify('Copié', 'success'); +} + // Définit la directive et le controller oVmap.module.directive('appUrlExporter', nsVmap.nsToolsManager.Urlexporter.prototype.urlExporterDirective); -oVmap.module.controller('AppUrlExporterController', nsVmap.nsToolsManager.Urlexporter.prototype.urlExporterController); \ No newline at end of file +oVmap.module.controller('AppUrlExporterController', nsVmap.nsToolsManager.Urlexporter.prototype.urlExporterController); diff --git a/src/module_vmap/module/javascript/app/vmap/vmap.js b/src/module_vmap/module/javascript/app/vmap/vmap.js index 48dbc1bacdb92c117848b877817f120614ccbc71..f178a8c8318359837bd33d27463450bfe7744ea8 100644 --- a/src/module_vmap/module/javascript/app/vmap/vmap.js +++ b/src/module_vmap/module/javascript/app/vmap/vmap.js @@ -97,6 +97,13 @@ oVmap.properties = {}; */ oVmap.oMap_ = {}; + +/** + * Objet which contains the mapComapre + * @type {nsVmap.MapCompare} + * @private + */ +oVmap.oMapCompare_ = {}; /** * Objet which contains the layers tools (on the left band) * @type {nsVmap.nsMapManager.MapManager} @@ -196,6 +203,7 @@ oVmap.init = function () { // Instenciation des objects Vmap oVmap.oMap_ = new nsVmap.Map(); + oVmap.oMapCompare_ = new nsVmap.MapCompare(); oVmap.oMapManager_ = new nsVmap.nsMapManager.MapManager(); oVmap.oToolsManager_ = new nsVmap.nsToolsManager.ToolsManager(); @@ -283,6 +291,12 @@ oVmap.vmapController = function ($sanitize) { * @api stable */ this.map = this['map'] = oVmap.getMap().getOLMap(); + /** + * The OpenLayers map + * @type {ol.Map} + * @api stable + */ + this.mapCompare = this['mapCompare'] = oVmap.getMapCompare().getOLMap(); /** * The current action on map @@ -362,6 +376,16 @@ oVmap.getMap = function () { return this.oMap_; }; +/** + * nsVmap.oMapCompare_ getter + * @return {nsVmap.MapCompare} Map to use to compare + * @export + * @api experimental + */ +oVmap.getMapCompare = function () { + return this.oMapCompare_; +}; + /** * nsVmap.oMapManager_ getter * @return {nsVmap.nsMapManager.MapManager} Tools fo layers @@ -719,6 +743,8 @@ oVmap.resizeLayerTools = function (animate) { if (goog.isDef(angular.element($('#olMap')).scope())) angular.element($('#olMap')).scope()['ctrl'].startAnimation(); + if (goog.isDef(angular.element($('#olMapCompare')).scope())) + angular.element($('#olMapCompare')).scope()['ctrl'].startAnimation(); var aItems = ["layertree", "layersorder", "maplegendcontainer"]; var iMarge = 0; @@ -851,6 +877,7 @@ oVmap.printElem = function (elem) { */ oVmap.maxResizeBottomBar = function () { angular.element($('#olMap')).scope()['ctrl'].startAnimation(); + angular.element($('#olMapCompare')).scope()['ctrl'].startAnimation(); $(".open-more-selection-info").toggleClass("reverse"); @@ -869,13 +896,15 @@ oVmap.maxResizeBottomBar = function () { */ oVmap.minResizeBottomBar = function () { angular.element($('#olMap')).scope()['ctrl'].startAnimation(); - + angular.element($('#olMapCompare')).scope()['ctrl'].startAnimation(); + if ($("#map-container").hasClass("open2")) { $("#map-container").removeClass("open2"); $("#bottombar").removeClass("open2"); $(".open-more-selection-info").removeClass("reverse"); } else if ($("#map-container").hasClass("open")) { $("#map-container").addClass("minus"); + $("#map-container-compare").addClass("minus"); } }; diff --git a/src/module_vmap/module/lang/lang-en.json b/src/module_vmap/module/lang/lang-en.json index fc1484e29b1d7924daf36b156634486aca812d54..29d2d9f92d85c94d9d0f1e4a057bb501cf571635 100644 --- a/src/module_vmap/module/lang/lang-en.json +++ b/src/module_vmap/module/lang/lang-en.json @@ -287,7 +287,12 @@ "FORM_ENABLE_GETFEATUREINFO_CONFIGURATION_VMAP_CONFIG": "Enable GetFeatureInfo selection", "FORM_SELECTION_BUFFER_CONFIGURATION_CONFIGURATION_VMAP_CONFIG": "Buffer (en mm sur l'écran)", "FORM_SELECTION_MAX_SCALE_BUFFER_CONFIGURATION_CONFIGURATION_VMAP_CONFIG": "Buffer maximum (en mètres sur le terrain)", - "TITLE_SNAPPING_CONFIGURATION_CONFIGURATION_VMAP_CONFIG": "Default snapping options", + "TITLE_SNAPPING_CONFIGURATION_CONFIGURATION_VMAP_CONFIG": "Snapping options", + "FORM_SNAPPING_LIMIT_CONFIGURATION_CONFIGURATION_VMAP_CONFIG": "Manimum limit of points per object", + "FORM_SNAPPING_TOLERANCE_CONFIGURATION_CONFIGURATION_VMAP_CONFIG": "Snapping tolerance (in pixels)", + "FORM_SNAPPING_TYPE_ACC_CONFIGURATION_CONFIGURATION_VMAP_CONFIG": "Default snapping type", + "FORM_SNAPPING_VISIBILITY_CONFIGURATION_CONFIGURATION_VMAP_CONFIG": "Selected objects visibility", + "FORM_SNAPPING_AVOID_SUPERPOSITIONS_CONFIGURATION_CONFIGURATION_VMAP_CONFIG": "Avoid superposition", "FORM_SNAPPING_DEFAUT_LIMIT_CONFIGURATION_CONFIGURATION_VMAP_CONFIG": "Manimum limit of points per object", "FORM_SNAPPING_DEFAUT_TOLERANCE_CONFIGURATION_CONFIGURATION_VMAP_CONFIG": "Snapping tolerance (in pixels)", "FORM_SNAPPING_DEFAUT_TYPE_ACC_CONFIGURATION_CONFIGURATION_VMAP_CONFIG": "Default snapping type", diff --git a/src/module_vmap/module/lang/lang-fr.json b/src/module_vmap/module/lang/lang-fr.json index 970eebf515a273666fd84369acf99d6700229a7a..82fca25d0f2fa89bab33f3cd82e694948c3b78cc 100644 --- a/src/module_vmap/module/lang/lang-fr.json +++ b/src/module_vmap/module/lang/lang-fr.json @@ -287,7 +287,12 @@ "FORM_ENABLE_GETFEATUREINFO_CONFIGURATION_VMAP_CONFIG": "Interrogation par GetFeatureInfo", "FORM_SELECTION_BUFFER_CONFIGURATION_CONFIGURATION_VMAP_CONFIG": "Buffer de sélection (en mm sur l'écran)", "FORM_SELECTION_MAX_SCALE_BUFFER_CONFIGURATION_CONFIGURATION_VMAP_CONFIG": "Buffer maximum (en mètres sur le terrain)", - "TITLE_SNAPPING_CONFIGURATION_CONFIGURATION_VMAP_CONFIG": "Options d'accrochage par défaut", + "TITLE_SNAPPING_CONFIGURATION_CONFIGURATION_VMAP_CONFIG": "Options d'accrochage", + "FORM_SNAPPING_LIMIT_CONFIGURATION_CONFIGURATION_VMAP_CONFIG": "Limite de points accrochables", + "FORM_SNAPPING_TOLERANCE_CONFIGURATION_CONFIGURATION_VMAP_CONFIG": "Tolérance d'accrochage (pixels)", + "FORM_SNAPPING_TYPE_ACC_CONFIGURATION_CONFIGURATION_VMAP_CONFIG": "Type d'accrochage", + "FORM_SNAPPING_VISIBILITY_CONFIGURATION_CONFIGURATION_VMAP_CONFIG": "Visibilité des zones d'accrochage", + "FORM_SNAPPING_AVOID_SUPERPOSITIONS_CONFIGURATION_CONFIGURATION_VMAP_CONFIG": "Eviter les superpositions", "FORM_SNAPPING_DEFAUT_LIMIT_CONFIGURATION_CONFIGURATION_VMAP_CONFIG": "Limite de points accrochables", "FORM_SNAPPING_DEFAUT_TOLERANCE_CONFIGURATION_CONFIGURATION_VMAP_CONFIG": "Tolérance d'accrochage (pixels)", "FORM_SNAPPING_DEFAUT_TYPE_ACC_CONFIGURATION_CONFIGURATION_VMAP_CONFIG": "Type d'accrochage", diff --git a/src/module_vmap/module/template/layers/mapmodal/maplistlitle.html b/src/module_vmap/module/template/layers/mapmodal/maplistlitle.html index 2089b99cf5622ae5d17850d76b84c3b77b3102f1..e2ff1e2f60b3b953a96db0e5bdbc0d59d69f50ab 100644 --- a/src/module_vmap/module/template/layers/mapmodal/maplistlitle.html +++ b/src/module_vmap/module/template/layers/mapmodal/maplistlitle.html @@ -32,6 +32,7 @@ <div ng-repeat="map in oTheme.maps| orderBy: 'name'"> <div ng-if="($index + 1) % 4 === 0" class="row"> <div url="{{map.url}}" + ng-if="!compare" title="{{map.description}}" class="col-md-3 margin-10 pointer opacity-hover underline-hover maplist-map" style="text-align: center; font-size: 12px;" @@ -43,8 +44,21 @@ <span>{{map.name}}</span> </div> </div> + <div url="{{map.url}}" + ng-if="compare" + title="{{map.description}}" + class="col-md-6 margin-10 pointer opacity-hover underline-hover maplist-map" + style="text-align: center; font-size: 12px;" + onclick="oVmap.getMapManager().loadCompareMap(this)" + data-dismiss="modal"> + + <div onclick="$('#maplistlitle-container').removeClass('open')" ng-class="{'border-black': map.compare === true}" style="overflow:hidden" ng-attr-title="{{map.description}}"> + <div class="img-map" style="background-image: url('{{map.thumbnail}}')"></div> + <span>{{map.name}}</span> + </div> + </div> </div> - <div ng-if="($index + 1) % 4 !== 0" + <div ng-if="($index + 1) % 4 !== 0 && !compare" url="{{map.url}}" title="{{map.description}}" class="col-md-3 margin-10 pointer opacity-hover underline-hover maplist-map" @@ -57,6 +71,19 @@ <span>{{map.name}}</span> </div> </div> + <div ng-if="($index + 1) % 4 !== 0 && compare" + url="{{map.url}}" + title="{{map.description}}" + class="col-md-6 margin-10 pointer opacity-hover underline-hover maplist-map" + style="text-align: center; font-size: 12px;" + onclick="oVmap.getMapManager().loadCompareMap(this)" + data-dismiss="modal"> + + <div onclick="$('#maplistlitle-container').removeClass('open')" ng-class="{'border-black': map.compare === true}" style="overflow:hidden" ng-attr-title="{{map.description}}"> + <div class="img-map" style="background-image: url('{{map.thumbnail}}')"></div> + <span>{{map.name}}</span> + </div> + </div> </div> </div> </div> diff --git a/src/module_vmap/module/template/tools/basictools.html b/src/module_vmap/module/template/tools/basictools.html index e85c74762d60d92d19a6b560d5811b7a178fad98..0321871288835fc992af7d5daaf74aba86e102d4 100644 --- a/src/module_vmap/module/template/tools/basictools.html +++ b/src/module_vmap/module/template/tools/basictools.html @@ -8,9 +8,9 @@ <div> <li role="presentation" style="position: inherit" class="basic-tools-dropdown"> <a class="basic-tools-element pointer" - title="Générateur d'URL" + title="Lien vers la carte en cours" onclick="oVmap.getToolsManager().getBasicTools().toggleTool(this)"> - <span class="icon-at" aria-hidden="true"></span> + <span class="fa fa-link" aria-hidden="true"></span> </a> <div app-url-exporter app-lang="ctrl.lang" app-map="ctrl.map" id="basic-tools-dropdown-urlexporter" @@ -19,6 +19,22 @@ </div> </li> </div> + <!-- Outil de comparaison --> + <div> + <li role="presentation" style="position: inherit" class="basic-tools-dropdown"> + <a class="basic-tools-element pointer" + id="map-compare-tool-btn" + title="Comparaison de carte" + onclick="oVmap.getToolsManager().getBasicTools().toggleTool(this)" + ng-class="{'active2':$root.compare_enabled}"> + <span class="icon-mirror" aria-hidden="true"></span> + </a> + <div app-compare-mode app-lang="ctrl.lang" app-map="ctrl.map" + id="basic-tools-dropdown-comapremode" + class="dropdown-menu basic-tools-dropdown-element no-padding"> + </div> + </li> + </div> <!-- Login de l'utilisateur --> <div class="right"> <li role="presentation" style="position: inherit" class="basic-tools-dropdown"> @@ -58,7 +74,7 @@ </a> <div app-print app-lang="ctrl.lang" app-map="ctrl.map" app-action="ctrl.currentAction" id="basic-tools-dropdown-print-content" - class="dropdown-menu basic-tools-dropdown-element basic-tools-dropdown-print-content"> + class="dropdown-menu basic-tools-dropdown-element basic-tools-dropdown-print-content"> </div> </li> </div> @@ -66,13 +82,13 @@ <div class="right"> <li role="presentation" style="position: inherit" class="basic-tools-dropdown"> <a class="basic-tools-element pointer" - id="basic-tools-dropdown-insert-btn" + id="basic-tools-dropdown-insert-btn" title="Insertion" onclick="oVmap.getToolsManager().getBasicTools().toggleTool(this)"> <span class="icon-add-feature" aria-hidden="true"></span> </a> <div app-insert app-lang="ctrl.lang" app-map="ctrl.map" app-action="ctrl.currentAction" - id="basic-tools-dropdown-insert-content" + id="basic-tools-dropdown-insert-content" class="dropdown-menu basic-tools-dropdown-element basic-tools-dropdown-select-content"> </div> </li> @@ -96,4 +112,4 @@ </ul> </div> </div> -</div> \ No newline at end of file +</div> diff --git a/src/module_vmap/module/template/tools/comparemapmanager.html b/src/module_vmap/module/template/tools/comparemapmanager.html new file mode 100644 index 0000000000000000000000000000000000000000..5400040928382b75fee2971115575455e96f07c6 --- /dev/null +++ b/src/module_vmap/module/template/tools/comparemapmanager.html @@ -0,0 +1,23 @@ +<!--Mode compare--> +<div class="row margin-sides-0 no-padding"> + <div class="margin-sides-20"> + <div> + <div class="checkbox checkbox-info checkbox-inline checkbox_margin"> + <input id="useCompareModeCheckbox" + type="checkbox" + style="cursor:pointer;" + title=">Activer / Désactiver le mode comparaison" + ng-model="ctrl.useCompareMode"> + <label for="useCompareModeCheckbox" + style="cursor:pointer" + title="Activer / Désactiver le mode comparaison"> + Activer / Désactiver le mode comparaison + </label> + </div> + </div> + </div> + <div ng-show="ctrl.useCompareMode" class="col-md-12"><hr></div> + <div ng-show="ctrl.useCompareMode" class="col-md-12 no-padding"> + <app-maplistlitle app-lang="ctrl.lang" app-maplistlitle-map="ctrl.map" data-compare="true"></app-maplistlitle> + </div> +</div> diff --git a/src/module_vmap/module/template/tools/insert.html b/src/module_vmap/module/template/tools/insert.html index 8011c69fe13be35cb5aa0684448a4108da9abb2b..b18ed5994bdc1bfbf72020ce20aae6262f22d3be 100644 --- a/src/module_vmap/module/template/tools/insert.html +++ b/src/module_vmap/module/template/tools/insert.html @@ -242,32 +242,69 @@ <h4 class="modal-title" data-translate="TITLE_SNAPPING_CONFIGURATION_CONFIGURATION_VMAP_CONFIG"></h4> </div> <div class="modal-body modal-body-big-with-footer-3 font-12"> - <div class="col-sm-6"> - <h5 data-translate="FORM_SNAPPING_DEFAUT_TYPE_ACC_CONFIGURATION_CONFIGURATION_VMAP_CONFIG"></h5> - <select class="form-control" - ng-model="ctrl.tmpSnapOptions.mode"> - <option value="segment_edge_node" data-translate="FORM_SNAPPING_METHOD_SEN_CONFIGURATION_CONFIGURATION_VMAP_CONFIG"></option> - <option value="edge_node" data-translate="FORM_SNAPPING_METHOD_EN_CONFIGURATION_CONFIGURATION_VMAP_CONFIG"></option> - <option value="node" data-translate="FORM_SNAPPING_METHOD_N_CONFIGURATION_CONFIGURATION_VMAP_CONFIG"></option> - </select> - </div> - <div class="col-sm-6"> - <h5 data-translate="FORM_SNAPPING_DEFAUT_TOLERANCE_CONFIGURATION_CONFIGURATION_VMAP_CONFIG"></h5> - <input type="number" class="form-control" ng-model="ctrl.tmpSnapOptions.tolerance"> - </div> - <div class="col-sm-6"> - <h5 data-translate="FORM_SNAPPING_DEFAUT_LIMIT_CONFIGURATION_CONFIGURATION_VMAP_CONFIG"></h5> - <input type="number" class="form-control" ng-model="ctrl.tmpSnapOptions.limit"> + <div class="row"> + <div class="col-sm-6"> + <h5 data-translate="FORM_SNAPPING_TYPE_ACC_CONFIGURATION_CONFIGURATION_VMAP_CONFIG"></h5> + <select class="form-control" + ng-model="ctrl.tmpSnapOptions.mode"> + <option value="segment_edge_node" data-translate="FORM_SNAPPING_METHOD_SEN_CONFIGURATION_CONFIGURATION_VMAP_CONFIG"></option> + <option value="edge_node" data-translate="FORM_SNAPPING_METHOD_EN_CONFIGURATION_CONFIGURATION_VMAP_CONFIG"></option> + <option value="node" data-translate="FORM_SNAPPING_METHOD_N_CONFIGURATION_CONFIGURATION_VMAP_CONFIG"></option> + </select> + </div> + <div class="col-sm-6"> + <h5 data-translate="FORM_SNAPPING_TOLERANCE_CONFIGURATION_CONFIGURATION_VMAP_CONFIG"></h5> + <input type="number" class="form-control" ng-model="ctrl.tmpSnapOptions.tolerance"> + </div> </div> - <div class="col-sm-6"> - <h5 data-translate="FORM_SNAPPING_DEFAUT_VISIBILITY_CONFIGURATION_CONFIGURATION_VMAP_CONFIG"></h5> - <div class="radio radio-inline"> - <input type="radio" name="vmap_insert_snap_visible" id="vmap_insert_snap_visible_1" ng-model="ctrl.tmpSnapOptions.visible" ng-value="true"> - <label for="vmap_insert_snap_visible_1">Oui</label> + <div class="row"> + <div class="col-sm-6"> + <h5 data-translate="FORM_SNAPPING_LIMIT_CONFIGURATION_CONFIGURATION_VMAP_CONFIG"></h5> + <input type="number" class="form-control" ng-model="ctrl.tmpSnapOptions.limit"> </div> - <div class="radio radio-inline"> - <input type="radio" name="vmap_insert_snap_visible" id="vmap_insert_snap_visible_2" ng-model="ctrl.tmpSnapOptions.visible" ng-value="false"> - <label for="vmap_insert_snap_visible_2">Non</label> + <div class="col-sm-6"> + <h5 data-translate="FORM_SNAPPING_VISIBILITY_CONFIGURATION_CONFIGURATION_VMAP_CONFIG"></h5> + <div class="radio radio-inline"> + <input type="radio" name="vmap_insert_snap_visible" id="vmap_insert_snap_visible_1" ng-model="ctrl.tmpSnapOptions.visible" ng-value="true"> + <label for="vmap_insert_snap_visible_1">Oui</label> + </div> + <div class="radio radio-inline"> + <input type="radio" name="vmap_insert_snap_visible" id="vmap_insert_snap_visible_2" ng-model="ctrl.tmpSnapOptions.visible" ng-value="false"> + <label for="vmap_insert_snap_visible_2">Non</label> + </div> + </div> + </div> + <div class="row"> + <div class="col-sm-6" ng-show="aAvoidSuperpositionsBOs.length > 0"> + <div class="row"> + <div class="col-sm-12 text-right"> + <h5 data-translate="FORM_SNAPPING_AVOID_SUPERPOSITIONS_CONFIGURATION_CONFIGURATION_VMAP_CONFIG"></h5> + </div> + </div> + <div class="row" + ng-repeat="bo in aAvoidSuperpositionsBOs"> + <div class="col-sm-5 text-right"> + <label>{{bo.bo_title}}</label> + </div> + <div class="col-sm-7 text-right"> + <div class="radio radio-inline"> + <input type="radio" + name="vmap_insert_snap_avoid_superpositions_{{$index}}" + id="vmap_insert_snap_avoid_superpositions_1_{{$index}}" + ng-model="ctrl.tmpSnapOptions.avoidSuperpositions[bo.bo_id]" + ng-value="true"> + <label for="vmap_insert_snap_avoid_superpositions_1_{{$index}}">Oui</label> + </div> + <div class="radio radio-inline"> + <input type="radio" + name="vmap_insert_snap_avoid_superpositions_{{$index}}" + id="vmap_insert_snap_avoid_superpositions_2_{{$index}}" + ng-model="ctrl.tmpSnapOptions.avoidSuperpositions[bo.bo_id]" + ng-value="false"> + <label for="vmap_insert_snap_avoid_superpositions_2_{{$index}}">Non</label> + </div> + </div> + </div> </div> </div> </div> diff --git a/src/module_vmap/module/template/tools/print.html b/src/module_vmap/module/template/tools/print.html index 0a1fd62b4dcf92147ce7b543f37d661637c5f70c..330a8b9c2733511e33358d8d02c6e41a6463122a 100644 --- a/src/module_vmap/module/template/tools/print.html +++ b/src/module_vmap/module/template/tools/print.html @@ -53,10 +53,18 @@ </select> <button type="button" + title="Modification de la zone d'impression sur la carte" class="btn btn-info btn-sm" style="margin-top: 10px" - ng-class="{'active': ctrl.currentAction === 'print-modifyPrintZone'}" + ng-class="{'active': managePrintZoneInProgress}" ng-click="ctrl.managePrintZone()"><span class="glyphicon glyphicon-move"></span></button> + <button type="button" + title="Modification de la zone d'impression sur la carte de comparaison" + ng-show="$root.compare_enabled" + class="btn btn-info btn-sm" + style="margin-top: 10px" + ng-class="{'active': manageComparePrintZoneInProgress}" + ng-click="ctrl.manageComparePrintZone()"><span class="glyphicon glyphicon-move"></span></button> <button type="submit" class="btn btn-info btn-sm" diff --git a/src/module_vmap/module/template/tools/select.html b/src/module_vmap/module/template/tools/select.html index 420c5b37e81360aa9fd3fcd128e1d46bb3f5e001..24ae5ca8505ff719e24f57588e36d5e262265c44 100644 --- a/src/module_vmap/module/template/tools/select.html +++ b/src/module_vmap/module/template/tools/select.html @@ -290,32 +290,69 @@ <h4 class="modal-title" data-translate="TITLE_SNAPPING_CONFIGURATION_CONFIGURATION_VMAP_CONFIG"></h4> </div> <div class="modal-body modal-body-big-with-footer-3 font-12"> - <div class="col-sm-6"> - <h5 data-translate="FORM_SNAPPING_DEFAUT_TYPE_ACC_CONFIGURATION_CONFIGURATION_VMAP_CONFIG"></h5> - <select class="form-control" - ng-model="ctrl.tmpSnapOptions.mode"> - <option value="segment_edge_node" data-translate="FORM_SNAPPING_METHOD_SEN_CONFIGURATION_CONFIGURATION_VMAP_CONFIG"></option> - <option value="edge_node" data-translate="FORM_SNAPPING_METHOD_EN_CONFIGURATION_CONFIGURATION_VMAP_CONFIG"></option> - <option value="node" data-translate="FORM_SNAPPING_METHOD_N_CONFIGURATION_CONFIGURATION_VMAP_CONFIG"></option> - </select> - </div> - <div class="col-sm-6"> - <h5 data-translate="FORM_SNAPPING_DEFAUT_TOLERANCE_CONFIGURATION_CONFIGURATION_VMAP_CONFIG"></h5> - <input type="number" class="form-control" ng-model="ctrl.tmpSnapOptions.tolerance"> - </div> - <div class="col-sm-6"> - <h5 data-translate="FORM_SNAPPING_DEFAUT_LIMIT_CONFIGURATION_CONFIGURATION_VMAP_CONFIG"></h5> - <input type="number" class="form-control" ng-model="ctrl.tmpSnapOptions.limit"> + <div class="row"> + <div class="col-sm-6"> + <h5 data-translate="FORM_SNAPPING_TYPE_ACC_CONFIGURATION_CONFIGURATION_VMAP_CONFIG"></h5> + <select class="form-control" + ng-model="ctrl.tmpSnapOptions.mode"> + <option value="segment_edge_node" data-translate="FORM_SNAPPING_METHOD_SEN_CONFIGURATION_CONFIGURATION_VMAP_CONFIG"></option> + <option value="edge_node" data-translate="FORM_SNAPPING_METHOD_EN_CONFIGURATION_CONFIGURATION_VMAP_CONFIG"></option> + <option value="node" data-translate="FORM_SNAPPING_METHOD_N_CONFIGURATION_CONFIGURATION_VMAP_CONFIG"></option> + </select> + </div> + <div class="col-sm-6"> + <h5 data-translate="FORM_SNAPPING_TOLERANCE_CONFIGURATION_CONFIGURATION_VMAP_CONFIG"></h5> + <input type="number" class="form-control" ng-model="ctrl.tmpSnapOptions.tolerance"> + </div> </div> - <div class="col-sm-6"> - <h5 data-translate="FORM_SNAPPING_DEFAUT_VISIBILITY_CONFIGURATION_CONFIGURATION_VMAP_CONFIG"></h5> - <div class="radio radio-inline"> - <input type="radio" name="vmap_select_snap_visible" id="vmap_select_snap_visible_1" ng-model="ctrl.tmpSnapOptions.visible" ng-value="true"> - <label for="vmap_select_snap_visible_1">Oui</label> + <div class="row"> + <div class="col-sm-6"> + <h5 data-translate="FORM_SNAPPING_LIMIT_CONFIGURATION_CONFIGURATION_VMAP_CONFIG"></h5> + <input type="number" class="form-control" ng-model="ctrl.tmpSnapOptions.limit"> </div> - <div class="radio radio-inline"> - <input type="radio" name="vmap_select_snap_visible" id="vmap_select_snap_visible_2" ng-model="ctrl.tmpSnapOptions.visible" ng-value="false"> - <label for="vmap_select_snap_visible_2">Non</label> + <div class="col-sm-6"> + <h5 data-translate="FORM_SNAPPING_VISIBILITY_CONFIGURATION_CONFIGURATION_VMAP_CONFIG"></h5> + <div class="radio radio-inline"> + <input type="radio" name="vmap_select_snap_visible" id="vmap_select_snap_visible_1" ng-model="ctrl.tmpSnapOptions.visible" ng-value="true"> + <label for="vmap_select_snap_visible_1">Oui</label> + </div> + <div class="radio radio-inline"> + <input type="radio" name="vmap_select_snap_visible" id="vmap_select_snap_visible_2" ng-model="ctrl.tmpSnapOptions.visible" ng-value="false"> + <label for="vmap_select_snap_visible_2">Non</label> + </div> + </div> + </div> + <div class="row"> + <div class="col-sm-6" ng-show="aAvoidSuperpositionsBOs.length > 0"> + <div class="row"> + <div class="col-sm-12 text-right"> + <h5 data-translate="FORM_SNAPPING_AVOID_SUPERPOSITIONS_CONFIGURATION_CONFIGURATION_VMAP_CONFIG"></h5> + </div> + </div> + <div class="row" + ng-repeat="bo in aAvoidSuperpositionsBOs"> + <div class="col-sm-5 text-right"> + <label>{{bo.bo_title}}</label> + </div> + <div class="col-sm-7 text-right"> + <div class="radio radio-inline"> + <input type="radio" + name="vmap_select_snap_avoid_superpositions_{{$index}}" + id="vmap_select_snap_avoid_superpositions_1_{{$index}}" + ng-model="ctrl.tmpSnapOptions.avoidSuperpositions[bo.bo_id]" + ng-value="true"> + <label for="vmap_select_snap_avoid_superpositions_1_{{$index}}">Oui</label> + </div> + <div class="radio radio-inline"> + <input type="radio" + name="vmap_select_snap_avoid_superpositions_{{$index}}" + id="vmap_select_snap_avoid_superpositions_2_{{$index}}" + ng-model="ctrl.tmpSnapOptions.avoidSuperpositions[bo.bo_id]" + ng-value="false"> + <label for="vmap_select_snap_avoid_superpositions_2_{{$index}}">Non</label> + </div> + </div> + </div> </div> </div> </div> diff --git a/src/module_vmap/module/template/tools/urlexporter.html b/src/module_vmap/module/template/tools/urlexporter.html index 8219c05115135bb301def37dcd88452878d5a06b..c10845a6e2310f0b48ee40f6479e40e21372608f 100644 --- a/src/module_vmap/module/template/tools/urlexporter.html +++ b/src/module_vmap/module/template/tools/urlexporter.html @@ -1,11 +1,30 @@ <!--UrlExporter--> <div class="row margin-sides-0 margin-10"> - <div class="col-md-3" ng-show="ctrl.properties.allow_public_connection"> - <input type="checkbox" ng-model="ctrl.usePublicToken" id="publicAccountCheckbox"> - <label for="publicAccountCheckbox" class="control-label">Public</label> - </div> - <div class="" ng-class="{'col-md-9' : ctrl.properties.allow_public_connection, 'col-md-12': !ctrl.properties.allow_public_connection}"> - <label for="urlExporterField" class="control-label">URL</label> - <input type="text" class="form-control" ng-model="ctrl.urlToExport" id="urlExporterField"> + <div class="col-md-12"> + <div class="left"> + <label for="urlExporterField" class="control-label">Lien vers la carte en cours</label> + </div> + <div class="right" ng-if="ctrl.properties.allow_public_connection"> + <div class="checkbox checkbox-info checkbox-inline"> + <input id="publicAccountCheckbox" + type="checkbox" + style="cursor:pointer;" + title=">Activer / Désactiver le mode public" + ng-model="ctrl.usePublicToken"> + <label for="publicAccountCheckbox" + style="cursor:pointer" + title="Activer / Désactiver le mode public"> + Public + </label> + </div> + </div> </div> -</div> \ No newline at end of file + <div class="col-md-12"> + <div class="input-group"> + <input type="text" class="form-control" ng-model="ctrl.urlToExport" id="urlExporterField"> + <span class="input-group-btn"> + <button type="button" class="btn btn-default" ng-click="ctrl.copyUrl()"><span class="icon-copy"></span></button> + </span> + </div> + </div> +</div> diff --git a/src/module_vmap/module/template/vmap.html b/src/module_vmap/module/template/vmap.html index 358cdd8b6ca49e2c506b886d9a79c2683830b5cb..0b1b12f973b55e61a0408e13faf08923522ef702 100755 --- a/src/module_vmap/module/template/vmap.html +++ b/src/module_vmap/module/template/vmap.html @@ -4,7 +4,7 @@ <div ng-if="!$root.is_mobile" id="left-sidebar" ng-class="vmapCtrl.left_open ? 'open' : ''"> <div id="maplistlitle-container" class="dropdown"> <!--voir dans maplistlitle.js pour l'evenement de fermeture de la dropdown--> - <button id="maplistlitle-button" class="btn btn-success dropdown-toggle btn-map-manager" + <button id="maplistlitle-button" class="btn btn-success dropdown-toggle btn-map-manager" type="button" onclick="$('#maplistlitle-container').toggleClass('open')"> <span class="icon-map left" style="font-size: 30px"></span> @@ -13,19 +13,19 @@ <span class="caret"></span> </span> </button> - - + + <div id="dropdownMenuMaps" class="dropdown-menu map-list-litle-panel"> <app-maplistlitle app-lang="ctrl.lang" app-maplistlitle-map="ctrl.map"></app-maplistlitle> <div id="map-manager-button-container" style="text-align: center"> - <button id="map-manager-button" - type="button" + <button id="map-manager-button" + type="button" class="btn btn-success btn-sm btn-modal margin-10" onclick="oVmap.simuleClick('btn-reload-myMap'); $('#mapModalManager').modal('show'); $('#dropdownMenuMaps').dropdown('toggle')"> GESTION DES CARTES - </button> + </button> </div> </div> </div> @@ -33,7 +33,7 @@ <div app-layertree app-map="vmapCtrl.map" app-proj="vmapCtrl.proj" app-lang="vmapCtrl.lang" id="app-layertree"></div> <div app-layersorder app-map="vmapCtrl.map" app-proj="vmapCtrl.proj" app-lang="vmapCtrl.lang" id="app-layersorder"></div> <div app-maplegend app-map="vmapCtrl.map" app-proj="vmapCtrl.proj" app-lang="vmapCtrl.lang" id="app-maplegend"></div> - <div id="LayersDiv"></div> + <div id="LayersDiv"></div> <!-- Map Modal --> <div class="modal fade" id="mapModalManager" role="dialog"> @@ -48,12 +48,19 @@ <div ng-if="!$root.is_mobile" id="opener-sidebar" ng-click="vmapCtrl.left_open = !vmapCtrl.left_open" onclick="oVmap.resizeLayerTools(false); oVmap.getToolsManager().getBasicTools().toggleOutTools();"> <div class="layer-tools-btn shadow-hover icon-tree" ng-class="vmapCtrl.left_open ? 'open' : ''" data-original-title="Couches et cartes"></div> </div> - + <!-- Carte --> - <div id="map-container" ng-class="ctrl.bottom_open ? 'open' : ''"> + <div id="map-container" + ng-class="{'open' : ctrl.bottom_open,'half' : compare_enabled, 'right-module-bar-present' : bLoadVmapModule, 'left-map-manager-open' : vmapCtrl.left_open, 'right-module-manager-open' : vmapCtrl.right_open}"> <app-map app-map="vmapCtrl.map" app-action="vmapCtrl.currentAction"></app-map> </div> + <!-- Carte Compare --> + <div ng-show="compare_enabled" id="map-container-compare" + ng-class="{'open' : ctrl.bottom_open,'half' : compare_enabled, 'right-module-bar-present' : bLoadVmapModule, 'left-map-manager-open' : vmapCtrl.left_open, 'right-module-manager-open' : vmapCtrl.right_open}"> + <app-map-compare app-map="vmapCtrl.mapCompare" app-action="vmapCtrl.currentAction" style="display:block; width:100%; height:100%;"></app-map-compare> + </div> + <!-- Bandeau de selection --> <div id="opener-bottombar" class="list-group-item active"> <div id="opener-bottombar-1" class="open-selection-info" ng-click="ctrl.bottom_open = !ctrl.bottom_open" onclick="oVmap.minResizeBottomBar()"></div> @@ -63,7 +70,3 @@ <div id="info-container" app-infocontainer app-infocontainer-lang="vmapCtrl.lang" app-infos="vmapCtrl.infos"></div> </div> </div> - - - - diff --git a/src/module_vmap/web_service/ws/BusinessObjects.class.inc b/src/module_vmap/web_service/ws/BusinessObjects.class.inc index 413f93e43ebbc728cbc4600f84d2cc8d85d05249..fa7ca58d1eaf4d159d82c3498a6c75caf20b1d79 100755 --- a/src/module_vmap/web_service/ws/BusinessObjects.class.inc +++ b/src/module_vmap/web_service/ws/BusinessObjects.class.inc @@ -697,10 +697,6 @@ class BusinessObjects extends Vmap { $sFileContents .= $aFileContents[$i] . ' '; } -// // Travail sur chacune des requêtes du fichier -// $aFileContents = explode(';', $sFileContents); -// $aFileContents = $this->cleanDataModelFileArray($aFileContents); - return $sFileContents; } @@ -1318,7 +1314,7 @@ class BusinessObjects extends Vmap { fclose($pFile); } - if ($this->aValues["Js"] != "") { + if (isset($this->aValues["Js"])) { $pFileJS = fopen($sDirPath . '/forms/ressources/' . $sFormName . '.js', 'w+'); if (fwrite($pFileJS, $this->aValues["Js"]) == FALSE) { writeToErrorLog('ERROR: ' . $sFormName . '.js save failed'); @@ -1326,7 +1322,7 @@ class BusinessObjects extends Vmap { fclose($pFileJS); } - if ($this->aValues["Css"] != "") { + if (isset($this->aValues["Css"])) { $pFileCSS = fopen($sDirPath . '/forms/ressources/' . $sFormName . '.css', 'w+'); if (fwrite($pFileCSS, $this->aValues["Css"]) == FALSE) { writeToErrorLog('ERROR: ' . $sFormName . '.css save failed'); @@ -1370,6 +1366,26 @@ class BusinessObjects extends Vmap { @unlink($sDirPath . "/forms/default.json"); $aFields = explode("|", $this->aValues['field']); $this->generateBusinessObjectForm($sBusinessObjectId, $sFormName, $aFields, $this->aValues['label']); + break; + case "Published_Delete": + + if (file_exists($sDirPath . "/forms/published.json")) { + @unlink($sDirPath . "/forms/published.json"); + } + if (file_exists($sDirPath . "/forms/ressources/published.js")) { + @unlink($sDirPath . "/forms/ressources/published.js"); + } + if (file_exists($sDirPath . "/forms/ressources/published.css")) { + @unlink($sDirPath . "/forms/ressources/published.css"); + } + + break; + case "Delete_JS": + + if (file_exists($sDirPath . "/forms/ressources/" . $sFormName . ".js")) { + @unlink($sDirPath . "/forms/ressources/" . $sFormName . ".js"); + } + break; } } diff --git a/src/module_vmap/web_service/ws/Querys.class.inc b/src/module_vmap/web_service/ws/Querys.class.inc index a5e4b7deed246263e5d67a6856fb62af7d503fa9..3aed39da27e23ba5bbe1615d9fa027c6127d5f48 100644 --- a/src/module_vmap/web_service/ws/Querys.class.inc +++ b/src/module_vmap/web_service/ws/Querys.class.inc @@ -515,14 +515,54 @@ class Querys extends Vmap { * ) * ) */ + /** + * @SWG\Get(path="/querys/{business_object_id}/diff_geometry", + * tags={"Querys"}, + * summary="Get business object form querys", + * description="Get the difference geom between intersect_geom and the BO using st_difference", + * operationId="GET", + * produces={"application/json", "application/x-vm-json"}, + * @SWG\Parameter( + * name="token", + * in="query", + * description="user token", + * required=true, + * type="string" + * ), + * @SWG\Parameter( + * name="business_object_id", + * in="path", + * description="business object id", + * required=true, + * type="integer" + * ), + * @SWG\Parameter( + * name="intersect_geom", + * in="query", + * description="EWKT intersect geometry", + * required=true, + * type="integer" + * ), + * @SWG\Response( + * response=200, + * description="Poprerties Response", + * @SWG\Schema(ref="#/definitions/users") + * ) + * ) + */ /** * get Querys * @return Querys */ function GET($bOnlyReturnStatus = FALSE) { - if (isset($this->aPath[3]) && ($this->aPath[3] == 'geometry')) { - return $this->getBoGeomsFromIntersect($this->aPath[2]); + if (($this->aPath[3] == 'geometry') || ($this->aPath[3] == 'diff_geometry')) { + if (($this->aPath[3] == 'geometry')) { + return $this->getBoGeomsFromIntersect($this->aPath[2]); + } + if (($this->aPath[3] == 'diff_geometry')) { + return $this->getBoDiffGeomFromIntersect($this->aPath[2]); + } } else if (isset($this->aPath[3])) { return $this->queryBusinessObject($this->aPath[3]); } else { @@ -597,7 +637,6 @@ class Querys extends Vmap { // Valeurs par défaut $intersect_column = empty($intersect_column) ? $geom_column : $intersect_column; -// $intersect_buffer = empty($intersect_buffer) ? 0.01 : $intersect_buffer; $geom_field = empty($geom_field) ? $intersect_column : $geom_field; $get_geom = empty($geom_field) || empty($get_geom) ? false : $get_geom; $use_intersect = empty($intersect_geom) || empty($intersect_column) ? false : true; @@ -1205,6 +1244,121 @@ class Querys extends Vmap { } } + /** + * Get the difference geometry with a business object intersecting intersect_geom + */ + function getBoDiffGeomFromIntersect($sBusinessObjectId) { + + if (!empty($this->oConnection->oError)) { + $aXmlRacineAttribute['status'] = 0; + $sMessage = $this->oConnection->oError->asDocument('', 'vitis', $this->aValues['sEncoding'], True, $aXmlRacineAttribute, $this->aValues['sSourceEncoding'], $this->aValues['output']); + $aReturn = array('sStatus' => $aXmlRacineAttribute['status'], "sMessage" => $sMessage); + return $aReturn['sMessage']; + } + if (empty($sBusinessObjectId) || empty($this->aValues['intersect_geom'])) { + $oError = new VitisError(0, 'Parameters business_object_id, intersect_geom required'); + $aXmlRacineAttribute['status'] = 0; + $sMessage = $oError->asDocument('', 'vitis', $this->aValues['sEncoding'], True, $aXmlRacineAttribute, $this->aValues['sSourceEncoding'], $this->aValues['output']); + $aReturn = array('sStatus' => $aXmlRacineAttribute['status'], "sMessage" => $sMessage); + return $aReturn['sMessage']; + } + + // Objet BusinessObject correspondant + $aPath = array('vmap', 'businessobjects', $sBusinessObjectId); + $aValues = array( + 'token' => $this->aValues['token'], + 'output' => 'application/json', + 'sEncoding' => 'UTF-8', + 'sSourceEncoding' => 'UTF-8', + 'my_vitis_id' => $sBusinessObjectId, + 'module' => 'vmap', + ); + $oBusinessObject = new BusinessObject($aPath, $aValues, $this->aProperties, $this->oConnection); + $oBusinessObject->GET(); + + // Vérifie l'éxistance de l'objet métier + if (empty($oBusinessObject->aFields['business_object_id'])) { + $oError = new VitisError(0, 'Business object ' . $sBusinessObjectId . ' not founded'); + $aXmlRacineAttribute['status'] = 0; + $sMessage = $oError->asDocument('', 'vitis', $this->aValues['sEncoding'], True, $aXmlRacineAttribute, $this->aValues['sSourceEncoding'], $this->aValues['output']); + $aReturn = array('sStatus' => $aXmlRacineAttribute['status'], "sMessage" => $sMessage); + return $aReturn['sMessage']; + } + + // Paramètres retenus dans l'url + $sSchema = $oBusinessObject->aFields['schema']; + $sTable = $oBusinessObject->aFields['table']; + $sIntersectGeom = $this->aValues['intersect_geom']; + $sInputFilter = $this->aValues['filter']; + + // Paramètres retenus dans le business object + $sGeomColumn = $oBusinessObject->aFields['geom_column']; + $sDatabase = $oBusinessObject->aFields['database']; + + // Base de données + if (!empty($sDatabase) && $sDatabase != $this->oConnection->oBd->base) { + $this->oConnection->oBd = new Vm($this->oConnection->oBd->login, $this->oConnection->oBd->mdp, $sDatabase, $this->oConnection->oBd->serveur, $this->oConnection->oBd->port, $this->oConnection->oBd->sgbd, $this->oConnection->oBd->sPageEncoding); + } + + // Projection de la colonne intersectée + $iColumnProj = $this->oConnection->oBd->getColumnSRID($sSchema, $sTable, $sGeomColumn); + if (empty($iColumnProj)) { + $iColumnProj = '2154'; + } + + // Paramètres de la requête + $aParams = array(); + $aParams['sSchema'] = array('value' => $sSchema, 'type' => 'schema_name'); + $aParams['sTable'] = array('value' => $sTable, 'type' => 'table_name'); + $aParams['sGeomColumn'] = array('value' => $sGeomColumn, 'type' => 'column_name'); + $aParams['sIntersectGeom'] = array('value' => $sIntersectGeom, 'type' => 'geometry'); + + // Filtre + $aFilter = array( + 'column' => $sGeomColumn, + 'compare_operator' => 'intersect', + 'compare_operator_options' => array( + 'source_proj' => $iColumnProj, + ), + 'value' => $sIntersectGeom + ); + + if (!empty($sInputFilter)) { + $aFilter = $this->addFilterOperator($sInputFilter, $aFilter); + } + + $aDecodedFilter = $this->decodeJSONFilter($aFilter, $sSchema, $sTable); + + $sSecuredFilter = $aDecodedFilter['request']; + foreach ($aDecodedFilter['params'] as $key => $value) { + $aParams[$key] = $value; + } + + $sSql = ' + WITH geoms AS ( + SELECT (ST_Dump(st_difference( + ST_GeomFromEWKT([sIntersectGeom]), + ST_Union([sGeomColumn]) + ))).geom AS geom + FROM [sSchema].[sTable] WHERE ' . $sSecuredFilter . ' + ) + SELECT ST_AsEWKT(geom) as diff_geom + FROM geoms + ORDER BY ST_Area(geom) DESC + LIMIT 1 + '; + + $oResult = $this->oConnection->oBd->executeWithParams($sSql, $aParams); + if ($this->oConnection->oBd->enErreur()) { + $aXmlRacineAttribute['status'] = 0; + writeToErrorLog($this->oConnection->oBd->getBDMessage()); + return json_encode(array('errorMessage' => 'Error while calculating diff geom')); + } else { + $aResult = $this->oConnection->oBd->getResultTableAssoc($oResult); + return json_encode($aResult); + } + } + /** * @SWG\Put(path="/querys/{business_object_id}", * tags={"Querys"}, diff --git a/src/vitis/client/javascript/app/controllers/htmlFormCtrl.js b/src/vitis/client/javascript/app/controllers/htmlFormCtrl.js old mode 100755 new mode 100644 diff --git a/src/vitis/client/javascript/app/controllers/initCtrl.js b/src/vitis/client/javascript/app/controllers/initCtrl.js old mode 100755 new mode 100644 index 48855c56c2092018d46d95c1faa98e94bc383767..70431eefb04a8ac083d1575ba2a078ca0641527f --- a/src/vitis/client/javascript/app/controllers/initCtrl.js +++ b/src/vitis/client/javascript/app/controllers/initCtrl.js @@ -20,6 +20,7 @@ goog.require("vitis.modules.main"); vitisApp.initCtrl = function ($scope, $log, $q, envSrvc, sessionSrvc, propertiesSrvc, userSrvc, $translate) { // Informe l'application que le contrôleur a été chargée. vitisApp.broadcast('appInitCtrlLoaded'); + /** * getMainTemplateUrl function. * Change le template de l'élément principal de l'application. @@ -98,6 +99,43 @@ vitisApp.initCtrl = function ($scope, $log, $q, envSrvc, sessionSrvc, properties }); }; + + /** + * connectFromUrl function. + * Connexion à l'application avec les identifiants passés dans l'url. + * @param {string} oConnexionId Identifiants de connexion + **/ + $scope.$root["connectWithTokenUrl"] = function () { + $log.info("connectFromUrl"); + // Demande de token pour l'utilisateur. + ajaxRequest({ + "method": "POST", + "url": oClientProperties["web_server_name"] + "/" + oClientProperties["services_alias"] + "/" + sessionSrvc["web_service"] + "/" + sessionSrvc["web_service_controller"], + "scope": $scope, + "success": function (response) { + if (response["data"]["status"] == 1) { + // Cache le message d'erreur. + //$scope["hideErrorAlert"](); + // Sauve les données du token. + //sessionSrvc["token"] = oUrlParams['token']; + sessionSrvc["validity_date"] = response["data"]["validity_date"]; + sessionStorage["session_token"] = sessionSrvc["token"]; + // Sauve les données de l'utilisateur. + userSrvc["login"] = response["data"]["user"]; + userSrvc["id"] = parseInt(response["data"]["user_id"]); + userSrvc["privileges"] = response["data"]["privileges"]; + sessionStorage["user_login"] = response["data"]["user"]; + sessionStorage["user_id"] = userSrvc["id"]; + sessionStorage["privileges"] = userSrvc["privileges"]; + sessionSrvc["saveSessionToLocalStorage"](); + // + deferred.resolve(); + } else + sessionSrvc["disconnect"](); + } + }); + }; + // Sauve le nom de l'application (pour les modes de l'utilisateur) //sessionStorage["application"] = document.location.pathname.split("/").pop(); @@ -114,6 +152,14 @@ vitisApp.initCtrl = function ($scope, $log, $q, envSrvc, sessionSrvc, properties var deferred = $q.defer(); var promise = deferred.promise; + if (goog.isDefAndNotNull(oUrlParams['token'])){ + sessionStorage['session_token'] = oUrlParams['token']; + sessionSrvc["token"] = oUrlParams['token']; + sessionSrvc["saveSessionToLocalStorage"](); + $scope.$root["connectWithTokenUrl"](); + } else + deferred.resolve(); + // Connexion avec les identifiants passés dans l'url (si le cookie avec le token n'existe pas). var aUrlParamsKeys = Object.keys(oUrlParams); if (sessionSrvc["getAppLocalStorageItem"]("session_token") === null && aUrlParamsKeys.indexOf("login") !== -1 && aUrlParamsKeys.indexOf("password") !== -1) diff --git a/src/vitis/client/javascript/app/controllers/loginCtrl.js b/src/vitis/client/javascript/app/controllers/loginCtrl.js index 4e6e14618cdf92462865f9f573dbee866c13f221..a5456b97fd5b71d25c13cb4c0405b816fa331263 100644 --- a/src/vitis/client/javascript/app/controllers/loginCtrl.js +++ b/src/vitis/client/javascript/app/controllers/loginCtrl.js @@ -432,6 +432,7 @@ vitisApp.loginCtrl = function ($scope, $translate, $rootScope, $q, sessionSrvc, $translate([sConnectionErrorMessage]).then(function (translations) { sConnectionErrorMessage = translations[sConnectionErrorMessage]; $scope["showErrorAlert"](sConnectionErrorMessage.replace('[IPAddress]', ipAddress)); + deferred.reject(); sConnectionErrorMessage = undefined; deferred.reject(); }); @@ -440,6 +441,12 @@ vitisApp.loginCtrl = function ($scope, $translate, $rootScope, $q, sessionSrvc, case 18: sConnectionErrorMessage = "FORM_LOGIN_CONNECTION_ERROR_MISSING_PRIVILEGES"; break; + // Base de données injoignable. + case 19: + sConnectionErrorMessage = "FORM_LOGIN_CONNECTION_ERROR_UNREACHABLE_DATABASE"; + $scope["showErrorAlert"](sConnectionErrorMessage); + deferred.reject(); + break; default: sConnectionErrorMessage = "FORM_LOGIN_CONNECTION_ERROR"; } diff --git a/src/vitis/client/javascript/app/script_client.js b/src/vitis/client/javascript/app/script_client.js index 1f56beac66fa8b60adbae277624b4c216d4d7af5..02bda1b163d823f778c284e186dd91a290c803f2 100644 --- a/src/vitis/client/javascript/app/script_client.js +++ b/src/vitis/client/javascript/app/script_client.js @@ -1725,4 +1725,34 @@ vitisApp.on('appInitCtrlLoaded', function () { } }); vitisApp.module.directive("appHideColumn", vitisApp.appHideColumn); + + /** + * addAjaxLoaderToElement function. + * Ajoute un loader Ajax à côté d'un élément HTML. + * @param {string} sElementId Id de l'élément html. + **/ + angular.element(vitisApp.appMainDrtv).scope()["addAjaxLoaderToElement"] = function (sElementId) { + $log.info("addAjaxLoaderToElement"); + var oElem = document.getElementById(sElementId); + if (oElem !== null) { + var oAjaxLoaderElem = document.createElement('span'); + oAjaxLoaderElem.className = "icon-refresh form-glyphicon-refresh-animate"; + oElem.parentNode.appendChild(oAjaxLoaderElem); + } + }; + + /** + * removeAjaxLoaderFromElement function. + * Supprime un loader Ajax placé à côté d'un élément HTML. + * @param {string} sElementId Id de l'élément html. + **/ + angular.element(vitisApp.appMainDrtv).scope()["removeAjaxLoaderFromElement"] = function (sElementId) { + $log.info("removeAjaxLoaderFromElement"); + var oElem = document.getElementById(sElementId); + if (oElem !== null) { + var oAjaxLoaderElem = oElem.parentNode.querySelector(".form-glyphicon-refresh-animate"); + if (oAjaxLoaderElem !== null) + oElem.parentNode.removeChild(oAjaxLoaderElem); + } + }; }); diff --git a/src/vitis/client/javascript/externs/formReader/formReaderCtrl.js b/src/vitis/client/javascript/externs/formReader/formReaderCtrl.js old mode 100755 new mode 100644 diff --git a/src/vitis/client/javascript/externs/formReader/formReaderDrtv.js b/src/vitis/client/javascript/externs/formReader/formReaderDrtv.js index 48e7a37a22b78e1f1154bcaec9471d51e4a1c3a5..6634f5d412bfaf450ee68f68effbc48cfdb46c43 100644 --- a/src/vitis/client/javascript/externs/formReader/formReaderDrtv.js +++ b/src/vitis/client/javascript/externs/formReader/formReaderDrtv.js @@ -2156,8 +2156,8 @@ formReader.appSubformGridDrtv = function ($timeout, $translate, propertiesSrvc, // Récupère lélément en sélectionné formReaderService['getWebServiceData'](oFormWebService).then(function (aResult) { + var oSubformDefinition = aResult[0]['bo_json_form']; - var sSubformJSDefinition = aResult[0]['bo_json_form_js']; var oSubformValues = {}; var sModalId = 'formreader_' + scope['sFormUniqueName'] + '_grid_subform_modal'; @@ -2224,7 +2224,7 @@ formReader.appSubformGridDrtv = function ($timeout, $translate, propertiesSrvc, } }); - formReaderService['showModalSubform'](sModalId, oSubformScope, oSubformDefinition, sSubformDefinitionName, oSubformValues, sSubformJSDefinition); + formReaderService['showModalSubform'](sModalId, oSubformScope, oSubformDefinition, sSubformDefinitionName, oSubformValues); }); }; @@ -2252,7 +2252,6 @@ formReader.appSubformGridDrtv = function ($timeout, $translate, propertiesSrvc, }; var sModalId = 'formreader_' + scope['sFormUniqueName'] + '_grid_subform_modal'; var oSubformDefinition = oBusinessObject['json_form'][0]; - var sSubformJSDefinition = oBusinessObject['json_form_js']; var sSubformDefinitionName = 'insert'; // Grise le champ contenant la valeur du parent @@ -2294,7 +2293,7 @@ formReader.appSubformGridDrtv = function ($timeout, $translate, propertiesSrvc, }); }); }; - formReaderService['showModalSubform'](sModalId, oSubformScope, oSubformDefinition, sSubformDefinitionName, oSubformValues, sSubformJSDefinition); + formReaderService['showModalSubform'](sModalId, oSubformScope, oSubformDefinition, sSubformDefinitionName, oSubformValues); }; /** diff --git a/src/vitis/client/javascript/externs/formReader/formReaderSrvc.js b/src/vitis/client/javascript/externs/formReader/formReaderSrvc.js index 613652f9c35ccf385e3b72c1c26432d8e0e8a09f..6ca6ef291e6a45bdf3b6298b998729bd7abddef5 100644 --- a/src/vitis/client/javascript/externs/formReader/formReaderSrvc.js +++ b/src/vitis/client/javascript/externs/formReader/formReaderSrvc.js @@ -1230,15 +1230,15 @@ formReader.formReaderService = function ($translate, $rootScope, $q, $log, $time * @param {object} oSubformDefinition * @param {object} oSubformDefinitionName * @param {object} oSubformValues - * @param {string|null} sSubformJSDefinition */ - "showModalSubform": function (sModalId, oSubformScope, oSubformDefinition, oSubformDefinitionName, oSubformValues, sSubformJSDefinition) { + "showModalSubform": function (sModalId, oSubformScope, oSubformDefinition, oSubformDefinitionName, oSubformValues) { $log.log("showModalSubform"); var sToken = this['sToken']; var oProperties = this['oProperties']; - var loadForm = function(){ + if (goog.isDefAndNotNull(oSubformScope['loadSubForm'])) { + oSubformScope['loadSubForm']({ 'sFormDefinitionName': oSubformDefinitionName, 'oFormDefinition': oSubformDefinition, @@ -1246,30 +1246,6 @@ formReader.formReaderService = function ($translate, $rootScope, $q, $log, $time 'oProperties': oProperties, 'sToken': sToken }); - } - - if (goog.isDefAndNotNull(oSubformScope['loadSubForm'])) { - - if (goog.isDefAndNotNull(sSubformJSDefinition)) { - var sUrl = sSubformJSDefinition; - oVmap.log("initHtmlForm : javascript assoc. to : " + sUrl); - loadExternalJs([sUrl], { - "callback": function () { - loadForm(); - try { - if (goog.isDef(constructor_form)) { - constructor_form(oSubformScope, sUrl); - } - } catch (e) { - oVmap.log("constructor_form does not exist"); - } - }, - "async": true, - "scriptInBody": true - }); - } else { - loadForm(); - } $('#' + sModalId).modal('show'); } diff --git a/src/vitis/client/javascript/externs/studio/javascript/app/JsonLoader.js b/src/vitis/client/javascript/externs/studio/javascript/app/JsonLoader.js index 8dd8de6819f10497d896707cbf05e14121fe00c2..ff0407e2f3e53237b80d512f0db73df6ba0b45f2 100755 --- a/src/vitis/client/javascript/externs/studio/javascript/app/JsonLoader.js +++ b/src/vitis/client/javascript/externs/studio/javascript/app/JsonLoader.js @@ -248,7 +248,7 @@ nsVFB.JsonLoader.prototype.jsonLoaderController.prototype.requestToJson = functi cmd = "Perso_Reset"; break; } - this_.putRequest(cmd, undefined, function (data) { + this_.putRequest(cmd, this_.$scope_["FormSelected"], undefined, function (data) { // Cas d'erreur du put if (goog.isDefAndNotNull(data['errorMessage'])) { @@ -584,18 +584,6 @@ nsVFB.JsonLoader.prototype.jsonLoaderController.prototype.save = function (succe oVFB.unselectAll(); tmp = oVFB.cleanFormToSave(tmp); - /*if ($("#boolean-JS-include").prop("checked")) { - tmp[this_.$rootScope_["selected_form_type"]]["javascript"] = true; - } else { - tmp[this_.$rootScope_["selected_form_type"]]["javascript"] = false; - } - - if ($("#boolean-CSS-include").prop("checked")) { - tmp[this_.$rootScope_["selected_form_type"]]["style"] = true; - } else { - tmp[this_.$rootScope_["selected_form_type"]]["style"] = false; - }*/ - if (this['applicationName'] === 'gtf') { tmp[this_.$rootScope_["selected_form_type"]]["name"] = "WSubform"; tmp["display"] = tmp[this_.$rootScope_["selected_form_type"]]; @@ -623,7 +611,7 @@ nsVFB.JsonLoader.prototype.jsonLoaderController.prototype.save = function (succe oVFB.valid = this.isValid(tmp); if (oVFB.valid && tmp !== null) { - this_.putRequest("Perso_Save", data, success, error); + this_.putRequest("Perso_Save", this_.$scope_["FormSelected"], data, success, error); } else { $["notify"](this_.$scope_["text"]["Loader"]["Notify"]["Validation_Error"] + ': ' + oVFB.aNotValid, {"className": "error", "autoHideDelay": oVFB.TimeNotify_}); } @@ -646,18 +634,6 @@ nsVFB.JsonLoader.prototype.jsonLoaderController.prototype.publish = function () // Supprime les elements selectionnés oVFB.unselectAll(); - /*if ($("#boolean-JS-include").prop("checked")) { - tmp[this_.$rootScope_["selected_form_type"]]["javascript"] = true; - } else { - tmp[this_.$rootScope_["selected_form_type"]]["javascript"] = false; - } - - if ($("#boolean-CSS-include").prop("checked")) { - tmp[this_.$rootScope_["selected_form_type"]]["style"] = true; - } else { - tmp[this_.$rootScope_["selected_form_type"]]["style"] = false; - }*/ - if (this['applicationName'] === 'gtf') { tmp[this_.$rootScope_["selected_form_type"]]["name"] = "WSubform"; tmp["display"] = tmp[this_.$rootScope_["selected_form_type"]]; @@ -669,7 +645,6 @@ nsVFB.JsonLoader.prototype.jsonLoaderController.prototype.publish = function () data.append("Css", oVFB.getCss()); var success = function () { -// $["notify"](this_.$scope_["text"]["Loader"]["Notify"]["SaveData"], {"className": "success", "autoHideDelay": oVFB.TimeNotify_}); var data = ""; var success = function () { this_.requestToJson(); @@ -679,17 +654,16 @@ nsVFB.JsonLoader.prototype.jsonLoaderController.prototype.publish = function () $["notify"](this_.$scope_["text"]["Loader"]["Notify"]["Publish_Error"] + status, {"className": "error", "autoHideDelay": oVFB.TimeNotify_}); }; - this_.putRequest(this_.$scope_["FormSelected"] + "_Published", data, success, error); + this_.putRequest(this_.$scope_["FormSelected"] + "_Published", this_.$scope_["FormSelected"], data, success, error); }; var error = function (data, status) { $["notify"](this_.$scope_["text"]["Loader"]["Notify"]["SaveData_Error"] + status, {"className": "error", "autoHideDelay": oVFB.TimeNotify_}); }; if (oVFB.valid) { if (this_.$scope_["FormSelected"] != "Default") { - this_.putRequest("Perso_Save", data, success, error); + this_.putRequest("Perso_Save", this_.$scope_["FormSelected"], data, success, error); } else { - this_.putRequest("Default_Published", data, success, error); - + this_.putRequest("Default_Published", this_.$scope_["FormSelected"], data, success, error); } } else { $["notify"](this_.$scope_["text"]["Loader"]["Notify"]["Validation_Error"], {"className": "error", "autoHideDelay": oVFB.TimeNotify_}); @@ -763,7 +737,7 @@ nsVFB.JsonLoader.prototype.jsonLoaderController.prototype.reset = function () { var error = function (data, status) { $["notify"](this_.$scope_["text"]["Loader"]["Notify"]["Reset_Error"] + status, {"className": "error", "autoHideDelay": oVFB.TimeNotify_}); }; - this_.putRequest(this_.$scope_["FormSelected"] + "_Reset", data, success, error); + this_.putRequest(this_.$scope_["FormSelected"] + "_Reset", this_.$scope_["FormSelected"], data, success, error); } } }); @@ -771,14 +745,63 @@ nsVFB.JsonLoader.prototype.jsonLoaderController.prototype.reset = function () { oVFB.studioMainController.prototype.moveBootboxModalToStudioContainer(oModal); }; +/** + * Remove the published form on the server + * + * @export + */ +nsVFB.JsonLoader.prototype.jsonLoaderController.prototype.deletePublishedForm = function () { + oVFB.log('nsVFB.JsonLoader.jsonLoaderController.deletePublishedForm'); + + var this_ = this; + var oModal = bootbox.confirm('<h4>' + this["text"]["InfoBulle"]["Published"]["DeletePublishedForm"] + ' ?</h4>', function (result) { + if (result === true) { + var data = ""; + var success = function () { + $["notify"](this_.$scope_["text"]["Loader"]["Notify"]["Delete"], {"className": "success", "autoHideDelay": oVFB.TimeNotify_}); + this_.requestToJson(); + }; + var error = function (data, status) { + $["notify"](this_.$scope_["text"]["Loader"]["Notify"]["Delete_Error"] + status, {"className": "error", "autoHideDelay": oVFB.TimeNotify_}); + }; + this_.putRequest('Published_Delete', 'Published', data, success, error); + } + }); +} + +/** + * Remove the form JS on the server + * + * @export + */ +nsVFB.JsonLoader.prototype.jsonLoaderController.prototype.deleteJS = function () { + oVFB.log('nsVFB.JsonLoader.jsonLoaderController.deleteJS'); + + var this_ = this; + var oModal = bootbox.confirm('<h4>' + this["text"]["InfoBulle"]["Perso"]["Delete_JS"] + ' ?</h4>', function (result) { + if (result === true) { + var data = ""; + var success = function () { + $["notify"](this_.$scope_["text"]["Loader"]["Notify"]["Delete_JS"], {"className": "success", "autoHideDelay": oVFB.TimeNotify_}); + this_.requestToJson(); + }; + var error = function (data, status) { + $["notify"](this_.$scope_["text"]["Loader"]["Notify"]["Delete_JS_Error"] + status, {"className": "error", "autoHideDelay": oVFB.TimeNotify_}); + }; + this_.putRequest('Delete_JS', this_.$scope_["FormSelected"], data, success, error); + } + }); +} + /** * Make a put request on the server * @param {string} cmd command to load (Perso_Save, Perso_Published, Default_Published, Perso_Reset etc...) + * @param {string} sForm form to update * @param {object} data FormData to send * @param {function} functSuccess function to load in case of success * @param {function} functError function to load in case of error */ -nsVFB.JsonLoader.prototype.jsonLoaderController.prototype.putRequest = function (cmd, data, functSuccess, functError) { +nsVFB.JsonLoader.prototype.jsonLoaderController.prototype.putRequest = function (cmd, sForm, data, functSuccess, functError) { oVFB.log('nsVFB.JsonLoader.prototype.jsonLoaderController.prototype.putRequest'); var url = ''; @@ -810,15 +833,6 @@ nsVFB.JsonLoader.prototype.jsonLoaderController.prototype.putRequest = function 'success': functSuccess, 'error': functError }); - -// this.$http_({ -// url: url, -// method: 'PUT', -// data: data, -// headers: { -// "Content-Type": "undefined" -// } -// }).success(functSuccess).error(functError); }; /** @@ -829,14 +843,34 @@ nsVFB.JsonLoader.prototype.jsonLoaderController.prototype.suggestGenerateForm = oVFB.log('nsVFB.JsonLoader.prototype.jsonLoaderController.prototype.suggestGenerateForm'); var this_ = this; - var oModal = bootbox.confirm('<h4>' + this.$scope_['text']['Loader']['Notify']['generate_form'] + '</h4>', function (result) { - if (result === true) { - this_.suggestColumnsToGenerateForm(); - } else { - this_['aSuggestedTableFields'] = []; - this_.generateFormByBusinessObject(); + var oModal = bootbox['dialog']({ + 'message': '<h4>' + this.$scope_['text']['Loader']['Notify']['generate_form'] + '</h4>', + 'buttons': { + 'cancel': { + 'label': this.$scope_['text']['Loader']['Cancel'], + 'className': 'btn-default', + 'callback': function(){ + this_.useEmptyForm(); + } + }, + 'create_empty': { + 'label': this.$scope_['text']['Loader']['CreateEmptyForm'], + 'className': 'btn-primary', + 'callback': function(){ + this_['aSuggestedTableFields'] = []; + this_.generateFormByBusinessObject(); + } + }, + 'generate_from_columns': { + 'label': this.$scope_['text']['Loader']['GenerateForm'], + 'className': 'btn-primary', + 'callback': function(){ + this_.suggestColumnsToGenerateForm(); + } + } } }); + // Déplace la popup dans l'élément principal du studio (sinon elle est masquée en mode plein écran). oVFB.studioMainController.prototype.moveBootboxModalToStudioContainer(oModal); }; @@ -860,10 +894,16 @@ nsVFB.JsonLoader.prototype.jsonLoaderController.prototype.useEmptyForm = functio 'javascript': false, 'name': 'custom-form', 'nb_cols': 12, - 'rows': [], + 'rows': [{ + 'fields': [] + }], 'title': '' }; + if (!goog.isArray(data)) { + data = []; + } + data[0] = { 'datasources': {} }; @@ -1017,7 +1057,7 @@ nsVFB.JsonLoader.prototype.jsonLoaderController.prototype.generateFormByBusiness var error = function (data, status) { $["notify"](this_.$scope_["text"]["Loader"]["Notify"]["Reset_Error"] + status, {"className": "error", "autoHideDelay": oVFB.TimeNotify_}); }; - this_.putRequest(this_.$scope_["FormSelected"] + "_Reset", {"field": sFieldsToUse, "label": afieldsLabel}, success, error); + this_.putRequest(this_.$scope_["FormSelected"] + "_Reset", this_.$scope_["FormSelected"], {"field": sFieldsToUse, "label": afieldsLabel}, success, error); } else { ajaxRequest({ @@ -1035,19 +1075,6 @@ nsVFB.JsonLoader.prototype.jsonLoaderController.prototype.generateFormByBusiness $["notify"](this_.$scope_["text"]["Loader"]["Notify"]["CreateJson_Error"] + status, {"className": "error", "autoHideDelay": oVFB.TimeNotify_}); } }); - -// this.$http_({ -// url: url, -// method: 'POST', -// data: { -// 'fields': sFieldsToUse, -// 'label': afieldsLabel -// } -// }).success(function () { -// this_.requestToJson(); -// }).error(function () { -// $["notify"](this_.$scope_["text"]["Loader"]["Notify"]["CreateJson_Error"] + status, {"className": "error", "autoHideDelay": oVFB.TimeNotify_}); -// }); } }; diff --git a/src/vitis/client/javascript/externs/studio/lang/lang-en.json b/src/vitis/client/javascript/externs/studio/lang/lang-en.json index f33be9b38476461cc2228befc9bf4eb5f7f860cb..b6d34b3729e50d6508ea9665f3c1446ae7cec112 100755 --- a/src/vitis/client/javascript/externs/studio/lang/lang-en.json +++ b/src/vitis/client/javascript/externs/studio/lang/lang-en.json @@ -10,6 +10,8 @@ "WabState": "State", "Validate": "Validate", "Cancel": "Cancel", + "GenerateForm": "Generate form", + "CreateEmptyForm": "Create empty form", "AddTab": "Add tab", "EditTab": "Edit", "RemoveTab": "Remove", @@ -34,6 +36,7 @@ "Button_gtf": "FME generated form" }, "Published": { + "DeletePublishedForm": "Delete published form", "Button": "Used form", "Button_gtf": "Used form" }, @@ -42,7 +45,8 @@ "Reload": "Reload files from server", "Publish": "Publish the custom form", "Reset": "Replace the custom form by the default form", - "Button": "Modification used form" + "Button": "Modification used form", + "Delete_JS": "Remove JavaScript" } }, "Form": { @@ -87,6 +91,10 @@ "ProblemId": "ID problem, try again or contact an admin", "Reset": "Was reset", "Reset_Error": "Error while resetting : ", + "Delete": "Le formulaire a été supprimé", + "Delete_Error": "Erreur lors de la suppression du formulaire : ", + "Delete_JS": "JavaScript file deleted", + "Delete_JS_Error": "Erorr while deleting JavaScript file : ", "Publish": " Has been published", "PublishAndSave": " Has been published and saved", "Publish_Error": "Error while publishing : ", diff --git a/src/vitis/client/javascript/externs/studio/lang/lang-fr.json b/src/vitis/client/javascript/externs/studio/lang/lang-fr.json index 43a99c1e47c1a55b798c6eaa2b4daedeaccfd126..ddaad2891c0fd4177698f0341e3e075d915290b3 100755 --- a/src/vitis/client/javascript/externs/studio/lang/lang-fr.json +++ b/src/vitis/client/javascript/externs/studio/lang/lang-fr.json @@ -10,6 +10,8 @@ "WabState": "État wab", "Validate": "Valider", "Cancel": "Annuler", + "GenerateForm": "Générer un formulaire", + "CreateEmptyForm": "Créer un formulaire vide", "AddTab": "Ajouter un onglet", "EditTab": "Éditer", "RemoveTab": "Supprimer", @@ -34,6 +36,7 @@ "Button_gtf": "Afficher le formulaire par défaut" }, "Published": { + "DeletePublishedForm": "Supprimer le formulaire publié", "Button": "Afficher le formulaire par publié", "Button_gtf": "Afficher le formulaire par publié" }, @@ -44,7 +47,8 @@ "Reset": "Remplacer le formulaire personnalisé par le formulaire par défaut", "ResetWab": "Regénérer le formulaire depuis la base", "Button": "Afficher le formulaire par personnalisé", - "Button_gtf": "Afficher le formulaire par personnalisé" + "Button_gtf": "Afficher le formulaire par personnalisé", + "Delete_JS": "Supprimer la partie JavaScript du formulaire" } }, "Form": { @@ -89,6 +93,10 @@ "ProblemId": "Problème d'ID, réessayer ou contacter un administrateur", "Reset": " a été réinitialisé", "Reset_Error": "Erreur lors de la réinitialisation : ", + "Delete": "Le formulaire a été supprimé", + "Delete_Error": "Erreur lors de la suppression du formulaire : ", + "Delete_JS": "Le fichier JavaScript a été supprimé", + "Delete_JS_Error": "Erreur lors de la suppression du fichier JavaScript : ", "Publish": " a été publié", "PublishAndSave": " a été publié et sauvegardé", "Publish_Error": "Erreur lors de la publication : ", diff --git a/src/vitis/client/javascript/externs/studio/less/studio.less b/src/vitis/client/javascript/externs/studio/less/studio.less index 39431d7eef77567589e097ec3edf7dc1e449092f..25844881140da28f02b1d7303efee582025d3138 100755 --- a/src/vitis/client/javascript/externs/studio/less/studio.less +++ b/src/vitis/client/javascript/externs/studio/less/studio.less @@ -3,7 +3,7 @@ To change this license header, choose License Headers in Project Properties. To change this template file, choose Tools | Templates and open the template in the editor. */ -/* +/* Created on : 5 janv. 2016, 12:08:09 Author : a_borghi */ @@ -23,7 +23,7 @@ and open the template in the editor. //@import (less) '../css/lib/bootstrap/css/bootstrap.css'; -//définit la taille de la fenêtre +//définit la taille de la fenêtre .app_window{ /*Skin scrollBar*/ ::-webkit-scrollbar { @@ -39,11 +39,11 @@ and open the template in the editor. ::-webkit-scrollbar-thumb { -webkit-border-radius: 10px; border-radius: 10px; - background: @studio-color-purple; - -webkit-box-shadow: inset 0 0 6px rgba(0,0,0,0.5); + background: @studio-color-purple; + -webkit-box-shadow: inset 0 0 6px rgba(0,0,0,0.5); } ::-webkit-scrollbar-thumb:window-inactive { - background: @studio-color-purple; + background: @studio-color-purple; } input[type=number]::-webkit-outer-spin-button, @@ -61,7 +61,7 @@ and open the template in the editor. /*Laisse une marge sous un composant*/ .element-margin { - margin-bottom: 10px; + margin-bottom: 10px; } //align un div sur la droite avec une petite marge @@ -199,19 +199,14 @@ and open the template in the editor. } // rend un élément non selectable -.unselectable { - -moz-user-select: none; - -khtml-user-select: none; - -webkit-user-select: none; - -o-user-select: none; -} - -// décalage pour les checkbox et radio -.checkbox_margin { - margin-left: 30px; +.unselectable { + -moz-user-select: none; + -khtml-user-select: none; + -webkit-user-select: none; + -o-user-select: none; } -// Permet à code Mirror de prendre toute la place dans la div +// Permet à code Mirror de prendre toute la place dans la div .CodeMirror { border: 1px solid #eee; height: auto; @@ -241,7 +236,7 @@ and open the template in the editor. } .invalid_input{ - background-color: rgba(255,0,0,0.5); + background-color: rgba(255,0,0,0.5); } /*th, td{ @@ -343,15 +338,6 @@ and open the template in the editor. font-size:11px } -.checkbox label::before, .checkbox label::after{ - width:13px; - height: 13px; -} - -.checkbox { - padding-left: 12px; -} - .collapser-form-wab-modal{ font-size: 40px; padding-top: 10px; @@ -359,8 +345,8 @@ and open the template in the editor. } .transition-form-wab-collapser{ - transition: width 0.5s; - //transition: display 1s; + transition: width 0.5s; + //transition: display 1s; } .form-tools-tree-container{ overflow-y: auto; @@ -381,4 +367,4 @@ and open the template in the editor. background-color: initial; top: initial; //border: initial; -} \ No newline at end of file +} diff --git a/src/vitis/client/javascript/externs/studio/templates/JsonLoader.html b/src/vitis/client/javascript/externs/studio/templates/JsonLoader.html index f5b18f1bbcdc94c3affda84e3f319650ca32def9..6e320cdab08eda903260ccea6a2e5c0effbf9041 100755 --- a/src/vitis/client/javascript/externs/studio/templates/JsonLoader.html +++ b/src/vitis/client/javascript/externs/studio/templates/JsonLoader.html @@ -1,8 +1,4 @@ <div class="panel panel-veremes" id="FilesURL"> - <!-- <div class="panel-heading unselectable" ng-click="ctrl.resize()">{{::ctrl.text.Title}} - <span ng-if="collapsed" id="colapse_uploader_icon" class="fa fa-angle-right fa-lg" style="float:right"></span> - <span ng-if="!collapsed" id="colapse_uploader_icon" class="fa fa-angle-down fa-lg" style="float:right"></span> - </div>--> <div class="panel-heading unselectable"> <!--Fichier--> <div class="btn-group dropdown margin-right-10"> @@ -50,6 +46,24 @@ {{::ctrl.text.InfoBulle.Perso.Publish}} </a> </li> + <li ng-hide="ctrl.buttonHide" + ng-show="(FormSelected === 'Perso' || FormSelected === 'Published') && ctrl.applicationName === 'vmap'"> + <a title="{{::ctrl.text.InfoBulle.Published.Delete}}" + href="javascript:void(0);" + ng-click="ctrl.deletePublishedForm()"> + <span class="fa icon-trash" aria-hidden="true"></span> + {{::ctrl.text.InfoBulle.Published.DeletePublishedForm}} + </a> + </li> + <li ng-hide="ctrl.buttonHide" + ng-show="(FormSelected === 'Perso' || FormSelected === 'Published') && ctrl.applicationName === 'vmap'"> + <a title="{{::ctrl.text.InfoBulle.Perso.Delete_JS}}" + href="javascript:void(0);" + ng-click="ctrl.deleteJS()"> + <span class="fa icon-trash" aria-hidden="true"></span> + {{::ctrl.text.InfoBulle.Perso.Delete_JS}} + </a> + </li> <li ng-hide="ctrl.buttonHide" ng-show="FormSelected === 'Perso'"> <a title="{{::ctrl.text.InfoBulle.Perso.Reset}}" href="javascript:void(0);" diff --git a/src/vitis/client/lang/lang-en.json b/src/vitis/client/lang/lang-en.json index 349fcf07df20a59f918709e36e4db469d4cfcffb..0038b8111b023f79ac39954b3ddc1e892fbeeb59 100644 --- a/src/vitis/client/lang/lang-en.json +++ b/src/vitis/client/lang/lang-en.json @@ -7,6 +7,7 @@ "FORM_LOGIN_CONNECTION_ERROR": "Connection failed. Incorrect user / password / domain or database not available", "FORM_LOGIN_CONNECTION_ERROR_FORBIDDEN_IP": "Connection failed. IP [IPAddress] forbiden", "FORM_LOGIN_CONNECTION_ERROR_MISSING_PRIVILEGES": "Connection failed. The user does not have the required privileges. Please contact your administrator.", + "FORM_LOGIN_CONNECTION_ERROR_UNREACHABLE_DATABASE": "The application is currently unavailable (database unreachable).", "FORM_LOGIN_REMEMBER_ME": "Remember connection?", "FORM_APP_STATUS_ERROR": "Unstable application", "FORM_VAS_STATUS_ERROR": "Unstable VAS", diff --git a/src/vitis/client/lang/lang-fr.json b/src/vitis/client/lang/lang-fr.json index 5c5eb178de24b151ef22b6b2e7c0701363bc0297..7dfe445bb0d0440f1fc6b9a0b41d979c21b9a308 100644 --- a/src/vitis/client/lang/lang-fr.json +++ b/src/vitis/client/lang/lang-fr.json @@ -7,6 +7,7 @@ "FORM_LOGIN_CONNECTION_ERROR": "Connexion refusée. Utilisateur / Mot de passe / domaine incorrect ou base de données non disponible.", "FORM_LOGIN_CONNECTION_ERROR_FORBIDDEN_IP": "Connexion refusée. Adresse IP [IPAddress] non autorisée", "FORM_LOGIN_CONNECTION_ERROR_MISSING_PRIVILEGES": "Connexion refusée. L'utilisateur ne dispose pas des privilèges requis. Merci de contacter votre administrateur.", + "FORM_LOGIN_CONNECTION_ERROR_UNREACHABLE_DATABASE": "L'application est actuellement indisponible (base de données injoignable).", "FORM_LOGIN_REMEMBER_ME": "Se souvenir de moi ?", "FORM_APP_STATUS_ERROR": "Application instable", "FORM_VAS_STATUS_ERROR": "VAS instable", diff --git a/src/vitis/client/less/htmlForm.less b/src/vitis/client/less/htmlForm.less index 10480f56b30c5eefffc323ea0264d948b3675294..99e18c281d2a56bae257aa96f5758214cc3b46c9 100755 --- a/src/vitis/client/less/htmlForm.less +++ b/src/vitis/client/less/htmlForm.less @@ -595,3 +595,16 @@ form .checkbox { .timepicker-picker > table, .bootstrap-datetimepicker-widget .picker-switch .table-condensed { margin: auto } + +// Loader ajax pour un element de formulaire. +.form-glyphicon-refresh-animate { + display: inline-block; + top: 3px !important; + left: 3px; + font-size: large; + font-weight: 800; + color: black; + -webkit-animation:spin 1.5s linear infinite; + -moz-animation:spin 1.5s linear infinite; + animation:spin 1.5s linear infinite; +} diff --git a/src/vitis/client/less/main.less b/src/vitis/client/less/main.less old mode 100755 new mode 100644 index d567b91f34adfab804aee576cdf68409e253dda4..56042ea63502decf8696aff10e5c6dc4cc2020da --- a/src/vitis/client/less/main.less +++ b/src/vitis/client/less/main.less @@ -1046,3 +1046,24 @@ div[data-app-html-form]>div[app-form-reader]>.modal>.modal-dialog{ /*@supports (-ms-accelerator:true) and (not (color:unset)) { .selector { property:value; } }*/ + +.checkbox { + padding-left: 12px; +} + +.checkbox_margin { + margin-left: 30px; +} + +.checkbox-inline label::before{ + top: 3px; + left: 1px +} +.checkbox-inline label::after{ + top: 2px; +} + +.checkbox label::before, .checkbox label::after{ + width:13px; + height: 13px; +} diff --git a/src/vitis/client/modules/vitis/forms/configuration/configuration_vitis_configuration.json b/src/vitis/client/modules/vitis/forms/configuration/configuration_vitis_configuration.json old mode 100755 new mode 100644 diff --git a/src/vitis/client/modules/vitis/forms/exploitation/exploitation_exploitation.json b/src/vitis/client/modules/vitis/forms/exploitation/exploitation_exploitation.json new file mode 100755 index 0000000000000000000000000000000000000000..a7b4cde99ba8412476eb7ffe7a66a37f9c7c9bed --- /dev/null +++ b/src/vitis/client/modules/vitis/forms/exploitation/exploitation_exploitation.json @@ -0,0 +1,160 @@ +{ + "search":{ + + }, + "update":{ + "name":"gtf_exploitation_shared_directory_update_form", + "title":"FORM_TITLE_EXPLOITATION_EXPLOITATION", + "initEvent":"initExploitationSharedDirectoryForm()", + "event":"", + "input_size":"xs", + "nb_cols":12, + "class":"project-directory-upload-form", + "rows":[ + { + "class":"shared-directory-treeview", + "fields":[ + { + "type":"treeview", + "name":"shared_directory", + "label":"", + "required":false, + "pattern":"", + "nb_cols":12, + "id":"shared_directory", + "options":{ + "showBorder":false, + "levels":0, + "showCheckbox":true, + "expandIcon":"glyphicon glyphicon-folder-close", + "collapseIcon":"glyphicon glyphicon-folder-open", + "highlightSelected":true, + "multiSelect":false, + "dataLoadingEvent": "sharedDirectoryTreeviewDataLoaded" + } + } + ] + }, + { + "fields":[ + { + "type":"button", + "class":"btn-ungroup btn-group-xs", + "nb_cols":12, + "buttons":[ + { + "type":"button", + "name":"btn_download_file", + "glyphicon":"download", + "class":"btn-primary btn-xs", + "event":"downloadFile()", + "tooltip": { + "title":"FORM_DOWNLOAD_FILE_EXPLOITATION_EXPLOITATION", + "placement": "bottom", + "trigger": "hover", + "container": "body" + }, + "visible":false + }, + { + "type":"button", + "name":"btn_refresh_treeview", + "glyphicon":"refresh", + "class":"btn-primary btn-xs", + "event":"refreshExploitationSharedDirectoryTreeview()", + "tooltip": { + "title":"FORM_RELOAD_DIRECTORY_EXPLOITATION_EXPLOITATION", + "placement": "bottom", + "trigger": "hover", + "container": "body" + } + }, + { + "type":"button", + "name":"btn_delete_file", + "glyphicon":"trash", + "class":"btn-primary btn-xs", + "event":"deleteSharedDirectoryFiles()", + "tooltip": { + "title":"FORM_DELETE_FILES_EXPLOITATION_EXPLOITATION", + "placement": "bottom", + "trigger": "hover" + } + } + ] + } + ] + }, + { + "class":"form-field-inline", + "fields":[ + { + "type":"upload", + "name":"file", + "label":"FORM_FILE_EXPLOITATION_EXPLOITATION", + "nb_cols":4 + }, + { + "type":"text", + "name":"directory_name", + "label":"FORM_DIRECTORY_EXPLOITATION_EXPLOITATION", + "nb_cols":4 + } + ] + }, + { + "class":"form-field-inline", + "fields":[ + { + "type":"button", + "class":"btn-ungroup btn-group-sm", + "nb_cols":4, + "buttons":[ + { + "type":"button", + "name":"btn_upload_file", + "label":"FORM_UPLOAD_FMW_FILE_EXPLOITATION_EXPLOITATION", + "event":"uploadSharedDirectoryFile()", + "class":"btn-primary" + } + ] + }, + { + "type":"button", + "class":"btn-ungroup btn-group-sm", + "nb_cols":4, + "buttons":[ + { + "type":"button", + "name":"btn_create_directory", + "label":"FORM_BTN_CREATE_DIRECTORY_EXPLOITATION_EXPLOITATION", + "event":"createSharedDirectoryFolder()", + "class":"btn-primary" + } + ] + } + ] + } + ] + }, + "insert":{ + + }, + "display":{ + "name":"gtf_exploitation_shared_directory_display_form", + "title":"FORM_TITLE_EXPLOITATION_EXPLOITATION", + "input_size":"xs", + "nb_cols":8, + "rows":[ + { + "fields":[ + { + "type":"hidden", + "name":"fmw_file", + "nb_cols":12 + } + ] + } + ] + } +} \ No newline at end of file diff --git a/src/vitis/client/modules/vitis/forms/user/user_vitis_user.json b/src/vitis/client/modules/vitis/forms/user/user_vitis_user.json old mode 100755 new mode 100644 diff --git a/src/vitis/client/modules/vitis/forms/users/users_vitis_users.json b/src/vitis/client/modules/vitis/forms/users/users_vitis_users.json old mode 100755 new mode 100644 diff --git a/src/vitis/client/modules/vitis/javascript/script_module.js b/src/vitis/client/modules/vitis/javascript/script_module.js old mode 100755 new mode 100644 index 1f0e99b41d538a838143044510f0016012a6f4ce..716b8de908bc4dfb057afe25e838d92aa2463531 --- a/src/vitis/client/modules/vitis/javascript/script_module.js +++ b/src/vitis/client/modules/vitis/javascript/script_module.js @@ -1211,7 +1211,9 @@ vitisApp.on('appMainDrtvLoaded', function () { '</div>', link: function (scope, element, attrs) { - scope.textValue = (goog.isDefAndNotNull(attrs["hidevalue"])) ? "" : scope["row"]["entity"][scope["col"]["field"]] + "%"; + scope.$watch("row.entity." + scope["col"]["field"], function(val){ + scope.textValue = (goog.isDefAndNotNull(attrs["hidevalue"])) ? "" : val + "%"; + }); if (goog.isDefAndNotNull(attrs["mode"])) element[0].firstChild.className = element[0].firstChild.className + " progress-bar-" + attrs["mode"]; @@ -1693,4 +1695,261 @@ vitisApp.on('appMainDrtvLoaded', function () { envSrvc["oFormValues"][envSrvc["sFormDefinitionName"]]["tr_status_method"] = sMethod; // l'event submit du formulaire sera appelé après cette fonction }; + + /** + * loadVitisExploitation function. + * Chargement des sections du mode "exploitation". + **/ + angular.element(vitisApp.appMainDrtv).scope()["loadVitisExploitation"] = function () { + // Injection des services. + var $log = angular.element(vitisApp.appMainDrtv).injector().get(["$log"]); + var envSrvc = angular.element(vitisApp.appWorkspaceListDrtv).injector().get(["envSrvc"]); + // + $log.info("loadVitisExploitation"); + // Passage en mode "Update" (pour afficher les sections). + envSrvc["sMode"] = "update"; + }; + + /** + * initExploitationSharedDirectoryForm function. + * Chargement de l'arborescence du répertoire partagé. + **/ + angular.element(vitisApp.appMainDrtv).scope()["initExploitationSharedDirectoryForm"] = function () { + // Injection des services. + var $log = angular.element(vitisApp.appMainDrtv).injector().get(["$log"]); + var $rootScope = angular.element(vitisApp.appMainDrtv).injector().get(["$rootScope"]); + var $timeout = angular.element(vitisApp.appMainDrtv).injector().get(["$timeout"]); + var formSrvc = angular.element(vitisApp.appMainDrtv).injector().get(["formSrvc"]); + var envSrvc = angular.element(vitisApp.appMainDrtv).injector().get(["envSrvc"]); + // + $log.info("initExploitationSharedDirectoryForm"); + // Attends la fin de l'affichage du 1er formulaire. + var clearListener = $rootScope.$on('formExtracted', function (event) { + // Supprime le "listener". + clearListener(); + // + $timeout(function () { + $rootScope["loadExploitationSharedDirectoryTreeviewData"]().then(function(aNodes){ + $rootScope.$emit("sharedDirectoryTreeviewDataLoaded", aNodes); + }); + }); + // Huteur du treeview. + var oFormElementDefinition = formSrvc["getFormElementDefinition"]("shared_directory", envSrvc["sFormDefinitionName"]); + document.getElementById(oFormElementDefinition["id"] + "_treeview").style.height = document.getElementById("container_mode_exploitation").clientHeight - 221 + "px"; + }); + }; + + /** + * refreshExploitationSharedDirectoryTreeview function. + * Recharge les données du treeview du répertoire partagé. + **/ + angular.element(vitisApp.appMainDrtv).scope()["refreshExploitationSharedDirectoryTreeview"] = function () { + // Injection des services. + var $log = angular.element(vitisApp.appMainDrtv).injector().get(["$log"]); + var $rootScope = angular.element(vitisApp.appMainDrtv).injector().get(["$rootScope"]); + var envSrvc = angular.element(vitisApp.appMainDrtv).injector().get(["envSrvc"]); + var formSrvc = angular.element(vitisApp.appMainDrtv).injector().get(["formSrvc"]); + // + $log.info("refreshExploitationSharedDirectoryTreeview"); + $rootScope["loadExploitationSharedDirectoryTreeviewData"]().then(function(aNodes){ + var oFormElementDefinition = formSrvc["getFormElementDefinition"]("shared_directory", envSrvc["sFormDefinitionName"]); + var oTreeviewOptions = $("#" + oFormElementDefinition["id"] + "_treeview")["treeview"](true)["options"]; + $("#" + oFormElementDefinition["id"] + "_treeview")["treeview"](true)["remove"](); + oTreeviewOptions["data"] = aNodes; + $("#" + oFormElementDefinition["id"] + "_treeview")["treeview"](oTreeviewOptions); + // Huteur du treeview. + document.getElementById(oFormElementDefinition["id"] + "_treeview").style.height = document.getElementById("container_mode_exploitation").parentElement.clientHeight - 221 + "px"; + }); + }; + + /** + * loadExploitationSharedDirectoryTreeviewData function. + * Charge les données du treeview du répertoire partagé. + **/ + angular.element(vitisApp.appMainDrtv).scope()["loadExploitationSharedDirectoryTreeviewData"] = function () { + // Injection des services. + var $log = angular.element(vitisApp.appMainDrtv).injector().get(["$log"]); + var $q = angular.element(vitisApp.appStatisticsFormDrtv).injector().get(["$q"]); + var propertiesSrvc = angular.element(vitisApp.appMainDrtv).injector().get(["propertiesSrvc"]); + // + $log.info("loadExploitationSharedDirectoryTreeviewData"); + var deferred = $q.defer(); + var promise = deferred.promise; + // Charge l'arborescence du répertoire partagé. + ajaxRequest({ + "method": "GET", + "url": propertiesSrvc["web_server_name"] + "/" + propertiesSrvc["services_alias"] + "/vitis/exploitations/SharedDirectory", + "success": function(response) { + if (response["data"]["status"] === 1) { + if (typeof (response["data"]) !== "undefined") + deferred.resolve(response["data"]["tree"]["data"]); + } + } + }); + return promise; + }; + + /** + * deleteSharedDirectoryFiles function. + * Charge les données du treeview du répertoire partagé. + **/ + angular.element(vitisApp.appMainDrtv).scope()["deleteSharedDirectoryFiles"] = function () { + // Injection des services. + var $log = angular.element(vitisApp.appMainDrtv).injector().get(["$log"]); + var $rootScope = angular.element(vitisApp.appMainDrtv).injector().get(["$rootScope"]); + var $translate = angular.element(vitisApp.appMainDrtv).injector().get(["$translate"]); + var propertiesSrvc = angular.element(vitisApp.appMainDrtv).injector().get(["propertiesSrvc"]); + var envSrvc = angular.element(vitisApp.appMainDrtv).injector().get(["envSrvc"]); + var formSrvc = angular.element(vitisApp.appMainDrtv).injector().get(["formSrvc"]); + // + $log.info("deleteSharedDirectoryFiles"); + var oFormElementDefinition = formSrvc["getFormElementDefinition"]("shared_directory", envSrvc["sFormDefinitionName"]); + var aFileList = $("#" + oFormElementDefinition["id"] + "_treeview")["treeview"](true)["getChecked"](); + if (aFileList.length > 0) { + var oOptions = { + "className": "modal-warning", + "message": "CONFIRM_DELETE_FILES_EXPLOITATION_EXPLOITATION", + "callback": function(bResponse) { + if (bResponse) { + // Liste des fichiers et répertoires à supprimer. + var aFilePathList = []; + for (var i = 0; i < aFileList.length; i++) { + if (typeof(aFileList[i]["path"]["nodes"] != "undefined")) + aFilePathList.push(aFileList[i]["path"]); + else + aFilePathList.push(aFileList[i]["path"] + "/" + aFileList[i]["name"]); + } + // Suppression des fichiers et répertoires. + ajaxRequest({ + "method": "DELETE", + "url": propertiesSrvc["web_server_name"] + "/" + propertiesSrvc["services_alias"] + "/vitis/exploitations/SharedDirectory", + "params": { + "idList": aFilePathList.join("|") + }, + "success": function(response) { + if (response["data"]["status"] == 1) { + // Message et rechargement du treeview. + $translate("SUCCESSFUL_OPERATION").then(function (sTranslation) { + $.notify(sTranslation, "success"); + $rootScope["refreshExploitationSharedDirectoryTreeview"](); + }); + } + else { + // Affichage de la fenêtre modale d'erreur. + $rootScope["modalWindow"]("dialog", response["data"]["errorMessage"], {"className": "modal-danger"}); + } + } + }); + } + } + } + $rootScope["modalWindow"]("confirm", "", oOptions); + } + }; + + /** + * createSharedDirectoryFolder function. + * Création d'un répertoire dans le répertoire partagé. + **/ + angular.element(vitisApp.appMainDrtv).scope()["createSharedDirectoryFolder"] = function () { + // Injection des services. + var $log = angular.element(vitisApp.appMainDrtv).injector().get(["$log"]); + var $translate = angular.element(vitisApp.appMainDrtv).injector().get(["$translate"]); + var $rootScope = angular.element(vitisApp.appMainDrtv).injector().get(["$rootScope"]); + var propertiesSrvc = angular.element(vitisApp.appMainDrtv).injector().get(["propertiesSrvc"]); + var envSrvc = angular.element(vitisApp.appMainDrtv).injector().get(["envSrvc"]); + var formSrvc = angular.element(vitisApp.appMainDrtv).injector().get(["formSrvc"]); + // + $log.info("createSharedDirectoryFolder"); + // Si un répertoire est sélectionné -> création à l'intérieur. + var sDirectoryPath = envSrvc["oFormValues"][envSrvc["sFormDefinitionName"]]["directory_name"]; + if (typeof(sDirectoryPath) == "string" && sDirectoryPath != "") { + var oFormElementDefinition = formSrvc["getFormElementDefinition"]("shared_directory", envSrvc["sFormDefinitionName"]); + var aFileList = $("#" + oFormElementDefinition["id"] + "_treeview")["treeview"](true)["getSelected"](); + if (aFileList.length > 0) + sDirectoryPath = aFileList[0]["path"] + "/" + sDirectoryPath; + // + var formData = new FormData(); + formData.append("directory_path", sDirectoryPath); + ajaxRequest({ + "method": "POST", + "url": propertiesSrvc["web_server_name"] + "/" + propertiesSrvc["services_alias"] + "/vitis/exploitations/SharedDirectory/Directory", + "data": formData, + "success": function(response) { + if (response["data"]["status"] == 1) { + // Message et rechargement du treeview. + $translate("SUCCESSFUL_OPERATION").then(function (sTranslation) { + $.notify(sTranslation, "success"); + $rootScope["refreshExploitationSharedDirectoryTreeview"](); + var sFormElementName = envSrvc['oFormDefinition'][envSrvc['sFormDefinitionName']]['name']; + document.querySelector("form[name='" + sFormElementName + "']").reset(); + }); + } + else { + // Affichage de la fenêtre modale d'erreur. + $rootScope["modalWindow"]("dialog", response["data"]["errorMessage"], {"className": "modal-danger"}); + } + } + }); + } + else { + // Affichage de la fenêtre modale d'erreur. + $rootScope["modalWindow"]("dialog", "FORM_NO_DIRECTORY_EXPLOITATION_EXPLOITATION", {"className": "modal-danger"}); + } + }; + + /** + * uploadSharedDirectoryFile function. + * Upload d'un fichier dans le répertoire partagé. + **/ + angular.element(vitisApp.appMainDrtv).scope()["uploadSharedDirectoryFile"] = function () { + // Injection des services. + var $log = angular.element(vitisApp.appMainDrtv).injector().get(["$log"]); + var $translate = angular.element(vitisApp.appMainDrtv).injector().get(["$translate"]); + var $rootScope = angular.element(vitisApp.appMainDrtv).injector().get(["$rootScope"]); + var propertiesSrvc = angular.element(vitisApp.appMainDrtv).injector().get(["propertiesSrvc"]); + var envSrvc = angular.element(vitisApp.appMainDrtv).injector().get(["envSrvc"]); + var formSrvc = angular.element(vitisApp.appMainDrtv).injector().get(["formSrvc"]); + // + $log.info("uploadSharedDirectoryFile"); + // Si un fichier est sélectionné -> upload. + var oFile = envSrvc["oFormValues"][envSrvc["sFormDefinitionName"]]["file"]; + if (typeof(oFile) != "undefined" && oFile["aFiles"].length > 0) { + // Upload dans un répertoire. + var sDirectoryPath = ""; + var oFormElementDefinition = formSrvc["getFormElementDefinition"]("shared_directory", envSrvc["sFormDefinitionName"]); + var aFileList = $("#" + oFormElementDefinition["id"] + "_treeview")["treeview"](true)["getSelected"](); + if (aFileList.length > 0) + sDirectoryPath = aFileList[0]["path"]; + // Création du formdata. + var formData = new FormData(); + formData.append("file", oFile["aFiles"][0]); + formData.append("directory_path", sDirectoryPath); + // + ajaxRequest({ + "method": "POST", + "url": propertiesSrvc["web_server_name"] + "/" + propertiesSrvc["services_alias"] + "/vitis/exploitations/SharedDirectory/File", + "data": formData, + "success": function(response) { + if (response["data"]["status"] == 1) { + // Message, rechargement du treeview, vidage du formulaire. + $translate("SUCCESSFUL_OPERATION").then(function (sTranslation) { + $.notify(sTranslation, "success"); + $rootScope["refreshExploitationSharedDirectoryTreeview"](); + var sFormElementName = envSrvc['oFormDefinition'][envSrvc['sFormDefinitionName']]['name']; + document.querySelector("form[name='" + sFormElementName + "']").reset(); + }); + } + else { + // Affichage de la fenêtre modale d'erreur. + $rootScope["modalWindow"]("dialog", response["data"]["errorMessage"], {"className": "modal-danger"}); + } + } + }); + } + else { + // Affichage de la fenêtre modale d'erreur. + $rootScope["modalWindow"]("dialog", "FORM_NO_FILE_EXPLOITATION_EXPLOITATION", {"className": "modal-danger"}); + } + }; }); \ No newline at end of file diff --git a/src/vitis/client/modules/vitis/lang/lang-en.json b/src/vitis/client/modules/vitis/lang/lang-en.json old mode 100755 new mode 100644 index c8132242ba9258b6005e2fd7d9f502e8311efd72..dc98a487ebd474dde8d906521ce10687fd6b5a2f --- a/src/vitis/client/modules/vitis/lang/lang-en.json +++ b/src/vitis/client/modules/vitis/lang/lang-en.json @@ -326,5 +326,21 @@ "FORM_BILLINGGROUP_USERS_BILLINGGROUP": "Name", "FORM_DESCRIPTION_USERS_BILLINGGROUP": "Description", "FORM_AVAILABLE_USER_USERS_BILLINGGROUP": "Available users", - "FORM_LINKED_USER_USERS_BILLINGGROUP": "Users linked to group" + "FORM_LINKED_USER_USERS_BILLINGGROUP": "Users linked to group", + "" : "", + "FORM_TITLE_EXPLOITATION_EXPLOITATION" : "Shared directory", + "FORM_DOWNLOAD_FILE_EXPLOITATION_EXPLOITATION" : "Download file", + "FORM_RELOAD_DIRECTORY_EXPLOITATION_EXPLOITATION" : "Reload directory", + "FORM_DELETE_FILES_EXPLOITATION_EXPLOITATION" : "Delete files", + "FORM_UPLOAD_FMW_FILE_EXPLOITATION_EXPLOITATION" : "Upload", + "FORM_FILE_EXPLOITATION_EXPLOITATION" : "File to upload", + "CONFIRM_DELETE_FILES_EXPLOITATION_EXPLOITATION" : "Delete selected files and directories ?", + "FORM_CREATE_DIRECTORY_EXPLOITATION_EXPLOITATION" : "Create a directory", + "FORM_DIRECTORY_EXPLOITATION_EXPLOITATION" : "Name of the directory to create", + "FORM_BTN_UPLOAD_FILE_EXPLOITATION_EXPLOITATION" : "Upload", + "FORM_BTN_CREATE_DIRECTORY_EXPLOITATION_EXPLOITATION" : "Create", + "FORM_NO_DIRECTORY_EXPLOITATION_EXPLOITATION" : "Please specify a name for the directory to create", + "FORM_NO_FILE_EXPLOITATION_EXPLOITATION" : "Please select a file to upload", + "DIRECTORY_CREATION_ERROR_EXPLOITATION_EXPLOITATION" : "Directory creation error", + "FILE_UPLOAD_ERROR_EXPLOITATION_EXPLOITATION" : "File creation error" } diff --git a/src/vitis/client/modules/vitis/lang/lang-fr.json b/src/vitis/client/modules/vitis/lang/lang-fr.json old mode 100755 new mode 100644 index a25cbd86a472840b7cd34f0aeb4db57686e83610..c752c00a89122b4ccf90a5bb275a952f7ebfc775 --- a/src/vitis/client/modules/vitis/lang/lang-fr.json +++ b/src/vitis/client/modules/vitis/lang/lang-fr.json @@ -328,5 +328,21 @@ "FORM_BILLINGGROUP_USERS_BILLINGGROUP": "Nom", "FORM_DESCRIPTION_USERS_BILLINGGROUP": "Description", "FORM_AVAILABLE_USER_USERS_BILLINGGROUP": "Utilisateurs disponibles", - "FORM_LINKED_USER_USERS_BILLINGGROUP": "Utilisateurs liés au groupe" + "FORM_LINKED_USER_USERS_BILLINGGROUP": "Utilisateurs liés au groupe", + "" : "", + "FORM_TITLE_EXPLOITATION_EXPLOITATION" : "Répertoire partagé", + "FORM_DOWNLOAD_FILE_EXPLOITATION_EXPLOITATION" : "Télécharger le fichier", + "FORM_RELOAD_DIRECTORY_EXPLOITATION_EXPLOITATION" : "Recharger le répertoire", + "FORM_DELETE_FILES_EXPLOITATION_EXPLOITATION" : "Supprimer les fichiers", + "FORM_UPLOAD_FMW_FILE_EXPLOITATION_EXPLOITATION" : "Uploader", + "FORM_FILE_EXPLOITATION_EXPLOITATION" : "Fichier à uploader", + "CONFIRM_DELETE_FILES_EXPLOITATION_EXPLOITATION" : "Supprimer les fichiers et répertoires sélectionnés ?", + "FORM_CREATE_DIRECTORY_EXPLOITATION_EXPLOITATION" : "Créer un dossier", + "FORM_DIRECTORY_EXPLOITATION_EXPLOITATION" : "Nom du dossier à créer", + "FORM_BTN_UPLOAD_FILE_EXPLOITATION_EXPLOITATION" : "Uploader", + "FORM_BTN_CREATE_DIRECTORY_EXPLOITATION_EXPLOITATION" : "Créer", + "FORM_NO_DIRECTORY_EXPLOITATION_EXPLOITATION" : "Veuiller spécifier un nom pour le dossier à créer", + "FORM_NO_FILE_EXPLOITATION_EXPLOITATION" : "Veuiller sélectionner un fichier à uploader", + "DIRECTORY_CREATION_ERROR_EXPLOITATION_EXPLOITATION" : "Erreur de création du dossier", + "FILE_UPLOAD_ERROR_EXPLOITATION_EXPLOITATION" : "Erreur pendant l'upload du fichier" } diff --git a/src/vitis/client/modules/vitis/less/main.less b/src/vitis/client/modules/vitis/less/main.less index 66adeeb6954871428c3685880d1a6a9bbb8ee302..bbfd6cb88daa780124cac53154b6278d493816d8 100755 --- a/src/vitis/client/modules/vitis/less/main.less +++ b/src/vitis/client/modules/vitis/less/main.less @@ -7,4 +7,5 @@ @import 'updateConfiguration.less'; @import 'users.less'; @import 'activeDirectoryTree.less'; -@import 'webServiceHelp.less'; \ No newline at end of file +@import 'webServiceHelp.less'; +@import 'sharedDirectory.less'; \ No newline at end of file diff --git a/src/vitis/client/modules/vitis/less/sharedDirectory.less b/src/vitis/client/modules/vitis/less/sharedDirectory.less new file mode 100755 index 0000000000000000000000000000000000000000..7672659599a8c4ad76d0f469e8114d4202d7a937 --- /dev/null +++ b/src/vitis/client/modules/vitis/less/sharedDirectory.less @@ -0,0 +1,3 @@ +.shared-directory-treeview .treeview { + overflow-y: auto; +} \ No newline at end of file diff --git a/src/vitis/vas/rest/class/aws_lib/AmazonAWS.class.inc b/src/vitis/vas/rest/class/aws_lib/AmazonAWS.class.inc old mode 100755 new mode 100644 index 67f30140fb630544249a97969ea0e7b51f7259c1..223a0534b6262627e65631e7905eb9256825f8b9 --- a/src/vitis/vas/rest/class/aws_lib/AmazonAWS.class.inc +++ b/src/vitis/vas/rest/class/aws_lib/AmazonAWS.class.inc @@ -13,6 +13,7 @@ Class AmazonAWS { public $sAwsRegion; public $aLastCurlRequestInfo; public $sHost; + public $sLogFilePath; // Chemin optionnel vers le fichier de log pour Amazon S3. private $sAwsAccessKeyId; private $sAwsSecretAccessKey; private $sHashingAlgorithmString; @@ -467,5 +468,18 @@ Class AmazonAWS { function generateAuthorizationHeader($sAlgorithm, $sCredentialScope, $sSignedHeaders, $sSignature) { return $sAlgorithm . ' Credential=' . $this->sAwsAccessKeyId . '/' . $sCredentialScope . ', SignedHeaders=' . $sSignedHeaders . ', Signature=' . $sSignature; } + + /** + * Write a message to the error log file. + * @param {string} $sMessage Message to write to the log file. + */ + function writeToErrorLog($sMessage) { + $aDebugBacktrace = debug_backtrace(); + $sLogMessage = '|ERROR|' . $aDebugBacktrace[1]['class'] . '::' . $aDebugBacktrace[1]['function'] . '| ' . $sMessage; + if (empty($this->sLogFilePath)) + writeToErrorLog($sLogMessage); + else + writeToLog($sLogMessage, $this->sLogFilePath); + } } ?> \ No newline at end of file diff --git a/src/vitis/vas/rest/class/aws_lib/AmazonS3.class.inc b/src/vitis/vas/rest/class/aws_lib/AmazonS3.class.inc old mode 100755 new mode 100644 index f9bfdb4dcc555ceb4122ffec2b794e4a3180b82f..32c7ed76f933ba2499f7cfa63c4a943cb4fa6bd9 --- a/src/vitis/vas/rest/class/aws_lib/AmazonS3.class.inc +++ b/src/vitis/vas/rest/class/aws_lib/AmazonS3.class.inc @@ -102,9 +102,6 @@ Class AmazonS3 extends AmazonAWS { } $sFullUrl = $sMethod . ' ' . $sUrl . ' HTTP/1.1'; - - error_log($sFullUrl); - return $this->generateAwsSignedHeaders($sFullUrl, $sBucketHost, self::API_COMPONENT_SERVICE, $aHeaders, $sRequestPayload, true, 'Now', true); } @@ -171,8 +168,10 @@ Class AmazonS3 extends AmazonAWS { // Transfert cURL. $sRequestResult = $this->curlRequest($sUrl, $sMethod, null, $aHeaders); // - if ($this->aLastCurlRequestInfo['http_code'] != 200) - writeToErrorLog($sRequestResult); + if ($this->aLastCurlRequestInfo['http_code'] != 200) { + $this->writeToErrorLog($this->formatS3ErrorMessage($sRequestResult)); + return false; + } else { if (!empty($sFilePath)) file_put_contents($sFilePath, $sRequestResult); @@ -191,24 +190,23 @@ Class AmazonS3 extends AmazonAWS { function uploadFile($sBucket, $sKey, $sFilePath) { if (file_exists($sFilePath)) { $sFileName = pathinfo($sFilePath, PATHINFO_BASENAME); - // Url vers le fichier. $sUrl = 'https://' . $sBucket . '.' . $this->sHost; - // Génération des entêtes pour la requete. $aPostData = $this->generatePostData($sBucket, $sKey); $aPostData['Content-Type'] = mime_content_type($sFilePath); $aPostData['file'] = new CurlFile(realpath($sFilePath), $aPostData['Content-Type'], $sFileName); - $aHeaders = array( 'Content-Type: multipart/form-data', ); - $sRequestResult = $this->curlRequest($sUrl, 'post', $aPostData, $aHeaders, true); - - if ($this->aLastCurlRequestInfo['http_code'] != 204) - writeToErrorLog($sRequestResult); + if ($this->aLastCurlRequestInfo['http_code'] != 204) { + $this->writeToErrorLog($this->formatS3ErrorMessage($sRequestResult)); + return false; + } } + else + return false; } /** @@ -229,10 +227,12 @@ Class AmazonS3 extends AmazonAWS { $aHeaders = $this->generateS3requestHeaders($sMethod, $sUrl, $sBucket, array('Content-Type: application/x-www-form-urlencoded'), ''); // Transfert cURL. $sRequestResult = $this->curlRequest($sUrl, $sMethod, null, $aHeaders); - //error_log($sRequestResult); - if ($this->aLastCurlRequestInfo['http_code'] != 200){ - writeToErrorLog("ERROR: ScanDir can't scan this prefix or this bucket"); - } else { + if ($this->aLastCurlRequestInfo['http_code'] != 200) { + $this->writeToErrorLog("ERROR: ScanDir can't scan this prefix or this bucket"); + $this->writeToErrorLog($this->formatS3ErrorMessage($sRequestResult)); + return false; + } + else { $oXMLContent= json_decode(json_encode(simplexml_load_string($sRequestResult)), true); $oFiles = $this->awsObjectListXmlToTree($oXMLContent, $bWithFileInfos); } @@ -332,14 +332,44 @@ Class AmazonS3 extends AmazonAWS { // Transfert cURL. $sRequestResult = $this->curlRequest($sUrl, $sMethod, null, $aHeaders); - if ($this->aLastCurlRequestInfo['http_code'] != 200){ - writeToErrorLog("ERROR: it's impossible to delete this key in this bucket"); - } else { + if ($this->aLastCurlRequestInfo['http_code'] != 200) { + $this->writeToErrorLog("ERROR: it's impossible to delete this key in this bucket"); + $this->writeToErrorLog($this->formatS3ErrorMessage($sRequestResult)); + } else $bReturn = true; - error_log($sRequestResult); - } return $bReturn; } + + /** + * Convert an error message returned by s3 (xml to object). + * @param {string} $sXmlErrorMessage Error message returned by s3 (xml format). + * @return object S3 Error + */ + function getS3ErrorObject($sXmlErrorMessage) { + $oSimpleXmlElement = simplexml_load_string($sXmlErrorMessage); + if (is_object($oSimpleXmlElement)) { + $oErrorMessage = new stdClass(); + foreach ($oSimpleXmlElement as $sProperty => $oValue) { + $oErrorMessage->$sProperty = $oValue->__toString(); + } + return $oErrorMessage; + } + else + return false; + } + + /** + * Format an error message returned by s3. + * @param {string} $sXmlErrorMessage Error message returned by s3 (xml format). + * @return string Error message + */ + function formatS3ErrorMessage($sXmlErrorMessage) { + $oErrorMessage = $this->getS3ErrorObject($sXmlErrorMessage); + if ($oErrorMessage !== false) + return ($oErrorMessage->Code . ' : ' . $oErrorMessage->Message); + else + return $sXmlErrorMessage; + } } ?> \ No newline at end of file diff --git a/src/vitis/vas/rest/class/vitis_lib/VitisError.class.inc b/src/vitis/vas/rest/class/vitis_lib/VitisError.class.inc index 0d61f69fcd02cf3cf89e8758a57bb2723d85eef4..1c52cfaa95a3a0479a910281e35cde8f25376703 100644 --- a/src/vitis/vas/rest/class/vitis_lib/VitisError.class.inc +++ b/src/vitis/vas/rest/class/vitis_lib/VitisError.class.inc @@ -4,7 +4,7 @@ require_once(__DIR__."/DbClass.class.inc"); class VitisError extends DbClass { - function __construct($iErrorId, $sMessage=""){ + function __construct($iErrorId, $sErrorMessage="", $sMessage = ''){ $this->aFields['errorCode']=$iErrorId; switch ($iErrorId){ case 1 : @@ -57,9 +57,17 @@ class VitisError extends DbClass { break; case 18 : $this->aFields['errorType']="Missing privileges"; + case 17 : + $this->aFields['errorType']="The request returned an error"; + break; + case 19 : + $this->aFields['errorType']="The database is unreachable"; break; } - $this->aFields['errorMessage']=$sMessage; //Message renvoyé par la base de donnée + $this->aFields['errorMessage']=$sErrorMessage; //Message renvoyé par la base de donnée + // Message d'erreur additionnel. + if (!empty($sMessage)) + $this->aFields['message'] = $sMessage; } } ?> \ No newline at end of file diff --git a/src/vitis/vas/rest/class/vmlib/BD.class.inc b/src/vitis/vas/rest/class/vmlib/BD.class.inc old mode 100755 new mode 100644 diff --git a/src/vitis/vas/rest/class/vmlib/error.inc b/src/vitis/vas/rest/class/vmlib/error.inc old mode 100755 new mode 100644 index b36e043d301409462ee479bed0ea211463bb8a54..13db7b08ff362840fee0ef2bd2d8b84d0c63b52b --- a/src/vitis/vas/rest/class/vmlib/error.inc +++ b/src/vitis/vas/rest/class/vmlib/error.inc @@ -19,6 +19,10 @@ define('ERROR_0008', "ERROR - Aucune méthode n'a permis d'affecté un moteur au // define('ERROR_0009', "ERROR - L'algorithme ne permet pas de retourner un numéro de moteur exploitable. Le numéro de moteur retourné n'est pas de type entier. Type de la valeur retournée par la méthode : "); // define('ERROR_0010', "ERROR - Le numéro du moteur retourné par l'algorithme n'existe pas dans la liste des moteurs disponible dans GTF."); define('ERROR_0011', "Erreur Le fichier [_FILES[sNomObjet][name]] n'est pas téléchargé sur le serveur"); +define('ERROR_0035', "Erreur de la suppression d'un processus d'une demande stoppée"); +define('ERROR_0036', "Erreur de la commande d'information d'un processus d'une demande stoppée"); +define('ERROR_0037', "Erreur pendant l'arrêt de la demande sur Fme Desktop."); +define('ERROR_0038', "Erreur pendant l'arrêt de la demande sur Fme Server."); // veremap/DownloadMaj.class.inc define('ERROR_0012', "Unable to write file"); diff --git a/src/vitis/vas/rest/class/vmlib/logUtil.inc b/src/vitis/vas/rest/class/vmlib/logUtil.inc old mode 100755 new mode 100644 index f1334250b8024768910a30fecc9ac5a58b72f681..d7474ff379d5a0cf1850ac78f8ab2f5712560450 --- a/src/vitis/vas/rest/class/vmlib/logUtil.inc +++ b/src/vitis/vas/rest/class/vmlib/logUtil.inc @@ -7,7 +7,7 @@ * Fonctions de mise en place de logs * * \author Olivier Gayte <olivier.gayte@veremes.com> - * \author Fr�d�ric Mauro + * \author Frédéric Mauro */ /* * Variable globale stockant une erreur. @@ -20,8 +20,8 @@ $sMessageLogError = ""; $sFolderLib = "vmlib"; /** * Converti une chaine ISO-8859-1 en UTF-8 - * \param $sString Cha�ne de caract�res � convertir. - * \return une chaine encod�e en UTF-8 + * \param $sString Chaîne de caractères à convertir. + * \return une chaine encodée en UTF-8 */ /* function Latin1ToUtf8($sString){ if( mb_detect_encoding($sString,"UTF-8, ISO-8859-1")!="UTF-8" ){ @@ -52,22 +52,45 @@ function writeToLog($sString, $sFileName) { return false; global $properties, $sMessageLogError, $sFolderLib; - // Fred 05/06/2013 : Si le r�pertoire de log n'existe pas : cr�ation + // Si le répertoire de log n'existe pas : création if (!is_dir(dirname($sFileName))) mkdir(dirname($sFileName), 0777, true); if (empty(pathinfo($sFileName, PATHINFO_EXTENSION))) return false; - + + // Add Date and User informations before writing message in log file loadLang($sFolderLib, $properties["language"], $sFolderLib . "/"); $sString = str_replace(chr(13), '[\n]', $sString); $sString = str_replace(chr(10), '[\n]', $sString); - $handle = fopen($sFileName, 'a'); if(isset($_SESSION['ses_Login']) && isset($_SERVER['REMOTE_ADDR']) && isset($_SERVER['REMOTE_PORT'])){ $sPrelog = date("d/n/Y H:i:s").' '.$_SESSION['ses_Login'].' '.$_SERVER['REMOTE_ADDR'] . ':' . $_SERVER['REMOTE_PORT']; } else { $sPrelog = date("d/n/Y H:i:s"); } - if (fwrite($handle, $sPrelog . $properties["log_delim"] . $sString . CR . LF) === false) { + + $sMessageLogtoWrite = $sPrelog . $properties["log_delim"] . $sString . CR . LF; + + // Rename old file if greater than porperties log_size (maximum log size to open it through app in Kb) + // Get size of Log file in bytes + $iLogFileSize = filesize($sFileName); + + if($iLogFileSize !== false){ + // get size of log message + $iMessageLength = strlen($sMessageLogtoWrite); + $iTotalSizeKb = ($iLogFileSize + $iMessageLength) / 1024; + // compare with porperties log_size (maximum log size to open it through app in Kb) + if($iTotalSizeKb >= $properties['log_size'] - 1){ + // Rename of the original file to split log and keep the possibility to read it through application + $sFileSplitName = str_replace(".log", "." . date("Y_m_d_U") . ".log", $sFileName); + if(!rename($sFileName, $sFileSplitName)){ + $sMessageLogError = ERROR_IMPOSSIBLE_WRITE . $sFileName . ERROR_RIGHTS_ON_FILE . " (" . $sString . ")."; + } + } + } + + // create if needed and open log file to write log message inside. + $handle = fopen($sFileName, 'a'); + if (fwrite($handle, $sMessageLogtoWrite) === false) { fclose($handle); if (is_writable($sFileName)) { $sMessageLogError = ERROR_IMPOSSIBLE_WRITE . $sFileName . ERROR_RIGHTS_ON_FILE . " (" . $sString . ")."; diff --git a/src/vitis/vas/rest/class/vmlib/phpUtil.inc b/src/vitis/vas/rest/class/vmlib/phpUtil.inc index 08c287ba00d806bb737927d08cdc2a9f5ca93229..dee4b832527ccda3d2af6ca01b50acc49085d063 100755 --- a/src/vitis/vas/rest/class/vmlib/phpUtil.inc +++ b/src/vitis/vas/rest/class/vmlib/phpUtil.inc @@ -203,9 +203,10 @@ function getFileName($sFullFileName) { *@file vmlib/phpUtil.inc *@param string $sFolder *@param string $sDestination + *@param string $sPassword *@return boolean */ -function createZip($sFolder, $sDestination, $sExtensionToExclude = '') { +function createZip($sFolder, $sDestination, $sExtensionToExclude = '', $sPassword = '', $bDeleteFiles = false) { if (!empty($sExtensionToExclude)) { $aExtensionToExclude = explode('|', $sExtensionToExclude); } else { @@ -222,6 +223,7 @@ function createZip($sFolder, $sDestination, $sExtensionToExclude = '') { $files = new RecursiveIteratorIterator( new RecursiveDirectoryIterator($sFolder), RecursiveIteratorIterator::LEAVES_ONLY ); + $aCompressedFiles = array(); foreach ($files as $name => $file) { if (!$file->isDir()) { $filePath = $file->getRealPath(); @@ -234,12 +236,23 @@ function createZip($sFolder, $sDestination, $sExtensionToExclude = '') { if (in_array($sExtension, $aExtensionToExclude)) { continue; } - $zip->addFile($filePath, $relativePath); + if ($zip->addFile($filePath, $relativePath)) + $aCompressedFiles[] = $filePath; + // Mot de passe. + if (!empty($sPassword)) + $zip->setEncryptionName($oFileInfo->getFilename(), ZipArchive::EM_AES_256, $sPassword); } } - $zip->close(); - + if ($zip->close()) { + // Suppression des fichiers compressés. + if ($bDeleteFiles) { + foreach ($aCompressedFiles as $sFilePath) { + if (file_exists($sFilePath)) + unlink($sFilePath); + } + } + } return file_exists($sDestination); } diff --git a/src/vitis/vas/rest/class/wab_lib/BusinessObject.class.inc b/src/vitis/vas/rest/class/wab_lib/BusinessObject.class.inc index 34c24838743268ee7a5b0f40694ddb4094775403..36ae854ee3dd0789c11f938c6eba90dda09a36bf 100755 --- a/src/vitis/vas/rest/class/wab_lib/BusinessObject.class.inc +++ b/src/vitis/vas/rest/class/wab_lib/BusinessObject.class.inc @@ -21,7 +21,6 @@ class WabBusinessObject { protected $aSql = array(); protected $bNoError = true; protected $sErrorMessage; - protected $aLastCurlRequestInfo = ""; /* * **************************************************** Class constructor @@ -32,7 +31,7 @@ class WabBusinessObject { public function __construct($oBd, $aTableInfo, $aValues, $aProperties, $className, $iId = null) { require 'BusinessObject.class.sql.inc'; - $this->aTableInfo = $aTableInfo; + //$this->aTableInfo = $aTableInfo; $this->oBd = $oBd; $this->aValues = $aValues; $this->aProperties = $aProperties; @@ -41,12 +40,30 @@ class WabBusinessObject { $this->history = ""; } + /* * **************************************************** + Sauve l'action réalisé par l'utilisateur + \sEvent : action réalisé (changement de statut...) + * **************************************************** */ + + private function addHistoryEvent($sEvent) { + $this->history .= date('d/m/Y H:i') . ' | ' . $_SESSION['ses_Login'] . ' | ' . $sEvent . PHP_EOL; + } - /* ***************************************************** + /* * **************************************************** Change le statut \sStatus : statut * **************************************************** */ - +/* + protected function setStatus($sStatus) { + // Mode insertion ? + if (!empty($this->iId)) + $this->bo_id = $this->iId; + // + $this->status = $sStatus; + $this->addHistoryEvent($this->status); + $this->save(); + } +*/ public function wabSetStatus($sSchema, $sTable, $sBoNameField, $mBoIdValue, $sStatusName, $sView = '') { require 'BusinessObject.class.sql.inc'; @@ -62,24 +79,20 @@ class WabBusinessObject { ); $oResultat = $this->oBd->executeWithParams($aSQL["getStatusId"], $aParams); - //$this->status = $this->oBd->objetSuivant($oResultat)->status_id; - $oStatus = $this->oBd->objetSuivant($oResultat); + $this->status = $this->oBd->objetSuivant($oResultat)->status_id; // ajout historique - //$this->addHistoryEvent($this->status); - //$this->addHistoryEvent($oStatus->name); - // UPDATE dans la table avec le boName + $this->addHistoryEvent($this->status); + // UPDATE dans la table avec le boName $sSql = $aSQL["updateStatus"]; $aParams = array( "SCHEMA" => array("value"=> $sSchema, "type"=> 'column_name'), "TABLE" => array("value"=> $sView, "type"=> 'column_name'), - "STATUS_ID" => array("value"=> $oStatus->status_id, "type"=> 'number'), + "STATUS_ID" => array("value"=> $this->status, "type"=> 'number'), "BOIDFIELD" => array("value"=> $sBoNameField, "type"=> 'column_name'), "BOID" => array("value"=> $mBoIdValue, "type"=> 'number') ); $this->oBd->executeWithParams($sSql, $aParams); - - $this->aValues["status_id"] = $oStatus->status_id; } public function wabGetStatus($sSchema, $sTable, $sBoNameField, $mBoIdValue) { @@ -96,28 +109,13 @@ class WabBusinessObject { $oResultat = $this->oBd->executeWithParams($sSql, $aParams); return $this->oBd->objetSuivant($oResultat)->name; } - - public function wabGetObject($sSchema, $sTable, $sBoNameField, $mBoIdValue){ - require 'BusinessObject.class.sql.inc'; - $aParams = array( - "SCHEMA" => array("value"=> $sSchema, "type"=> 'column_name'), - "TABLE" => array("value"=> $sTable, "type"=> 'column_name'), - "BOIDFIELD" => array("value"=> $sBoNameField, "type"=> 'column_name'), - "BOID" => array("value"=> $mBoIdValue, "type"=> 'number') - ); - - $oResultat = $this->oBd->executeWithParams($aSQL["getBoValues"], $aParams); - $oFields = (array) $this->oBd->objetSuivant($oResultat); - - return $oFields; - } /* * ******************************************************************** Ajoute une note \sLineAttribute : Champ de form. contenant la note à ajouter \sNoteAttribute : Champ de form. contenant l'historique des notes * ******************************************************************** */ - public function addNote($sLineAttribute, $sNoteAttribute) { + protected function addNote($sLineAttribute, $sNoteAttribute) { if (!empty($this->aValues[$sLineAttribute])) { // Mode insertion ? if (!empty($this->iId)) @@ -223,10 +221,8 @@ class WabBusinessObject { * ******************************************************************** */ function save() { - //$aValues = $this->getClassParameters(); - //$this->oBd->update($this->aTableInfo['schema_name'], str_replace($this->aTableInfo["module"] . "_", "", $this->aTableInfo['name']), $aValues, $this->aTableInfo['id_field'], $this->bo_id, $this->aTableInfo['id_field_type']); - $aValues = $this->getClassParameters(); - $this->oBd->update($this->aTableInfo['schema_name'], $this->aTableInfo['name'], $aValues, $this->aTableInfo['id_field'], $this->bo_id, $this->aTableInfo['id_field_type']); + $aValues = $this->getClassParameters(); + $this->oBd->update($this->aTableInfo['schema_name'], str_replace($this->aTableInfo["module"] . "_", "", $this->aTableInfo['name']), $aValues, $this->aTableInfo['id_field'], $this->bo_id, $this->aTableInfo['id_field_type']); } /* * ******************************************************************** @@ -257,38 +253,44 @@ class WabBusinessObject { $bNoError = true; - //get workspace id - $sSQL = "SELECT workspace_id FROM [SCHEMA_GTF].workspace WHERE key = [WK_KEY];"; - $aParams = array( - "SCHEMA_GTF" => array('value'=> $this->aProperties["schema_gtf"], 'type' => 'column_name'), - "WK_KEY" => array('value'=> $sWorkspaceKey, 'type' => 'string'), - ); - $oWK = $this->oBd->executeWithParams($sSQL, $aParams); - // oBd en erreur - $iWKid = $this->oBd->objetSuivant ($oWK)->workspace_id; - // Insertion de la demande - $sUrl = $this->aProperties['web_server_name'] . '/' . $this->aProperties['services_alias'] . '/gtf/userorders'; - $postfields = array( - //'token'=>$sToken, - 'order_date' => date('Y-m-d'), - 'workspace_id'=>$iWKid, - 'priority_id'=>$iPriorityId, - 'email_option_id'=>$iEmailOptionId, - 'wk_params'=>$sWkParams, - 'xslstylesheet'=>$sXslStyleSheet - ); - - if ( $sEmailNotifications != null){ - $postfields['email_notifications'] = $sEmailNotifications; + if($properties['web_server_name'] === "[HTTP_HOST]"){ + $properties['web_server_name'] = "https://localhost"; } - - $oReturn = $this->contactCurrentApi("POST", 'gtf/userorders', $postfields , $sMode="json"); - - error_log(print_r($oReturn, true)); - if($oReturn === false){ + // Get token + $sToken = $this->getToken(); + + if ($sToken !== false) { + + //get workspace id + $sSQL = "SELECT workspace_id FROM [SCHEMA_GTF].workspace WHERE key = [WK_KEY];"; + $aParams = array( + "SCHEMA_GTF" => array('value'=> $this->aProperties["schema_gtf"], 'type' => 'column_name'), + "WK_KEY" => array('value'=> $sWorkspaceKey, 'type' => 'string'), + ); + $oWK = $this->oBd->executeWithParams($sSQL, $aParams); + // oBd en erreur + $iWKid = $this->oBd->objetSuivant ($oWK)->workspace_id; + // Insertion de la demande + $sUrl = $this->aProperties['web_server_name'] . '/' . $this->aProperties['services_alias'] . '/gtf/userorders'; + $postfields = array( + 'token'=>$sToken, + 'order_date' => date('Y-m-d'), + 'workspace_id'=>$iWKid, + 'priority_id'=>$iPriorityId, + 'email_option_id'=>$iEmailOptionId, + 'wk_params'=>$sWkParams, + 'xslstylesheet'=>$sXslStyleSheet + ); + + if ( $sEmailNotifications != null){ + $postfields['email_notifications'] = $sEmailNotifications; + } + + $oReturn = $this->postCurlRequest ($sUrl, $postfields); + + } else $sErrorMsg = 'Error while performing a cURL session (' . __METHOD__ . ' (get token))'; - } if ($sErrorMsg != '') { writeToErrorLog($sErrorMsg); @@ -347,41 +349,32 @@ class WabBusinessObject { /Retour : string token * ******************************************************************** */ - function getToken ($sServerRestUrl = '', $aAuthParams = null) { - - if($this->aProperties['web_server_name'] === "[HTTP_HOST]"){ - $this->aProperties['web_server_name'] = "https://localhost"; - } + function getToken () { - if(empty($sServerRestUrl)){ - $sServerRestUrl = $this->aProperties['web_server_name'] . '/' . $this->aProperties['services_alias']; - } + if($this->aProperties['web_server_name'] === "[HTTP_HOST]"){ + $this->aProperties['web_server_name'] = "https://localhost"; + } + $sUrl = $this->aProperties['web_server_name'] . '/' . $this->aProperties['services_alias'] . '/vitis/privatetoken'; - $sUrl = $sServerRestUrl . '/vitis/privatetoken'; - - if(!empty($aAuthParams)){ - $postfields = $aAuthParams; - } else if(!empty($_SESSION["ses_Login"])){ + if(!empty($_SESSION["ses_Login"])){ $sUserPassword = trim(des(rtrim(utf8_decode($_SESSION['ses_Login'])), hexToString(rtrim($_SESSION['ses_Password'])), 0, 0, null)); $postfields = array('user'=>$_SESSION["ses_Login"], 'password'=>$sUserPassword); } else { $postfields = array('user'=>$this->aProperties["login_bot"], 'password'=>$this->aProperties["pass_bot"]); } - //$oToken = json_decode($this->postCurlRequest ($sUrl, $postfields)); - $oToken = json_decode($this->sendCurlRequest ("POST", $sUrl, json_encode($postfields), array("Accept: applicaton/json", "Content-Type: application/json"))); - + $oToken = json_decode($this->postCurlRequest ($sUrl, $postfields)); return $oToken->token; } /* * ******************************************************************** - envoi une requete curl en POST (DEPRECATED) + envoi une requete curl en POST \$sUrl : Url pour envoyer la requete \$postfields : array contenant les paramètres à envoyer /Retour : string token * ******************************************************************** */ function postCurlRequest ($sUrl, $postfields) { - /*$ch = curl_init($sUrl); + $ch = curl_init($sUrl); curl_setopt($ch, CURLOPT_CONNECTTIMEOUT, 5); curl_setopt($ch, CURLOPT_HTTPHEADER, array("Accept: application/json")); curl_setopt($ch, CURLOPT_RETURNTRANSFER, true); @@ -389,153 +382,9 @@ class WabBusinessObject { curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false); curl_setopt($ch, CURLOPT_POSTFIELDS, $postfields); curl_setopt($ch, CURLOPT_SSL_VERIFYHOST, 0); - return curl_exec($ch);*/ - $this->sendCurlRequest("POST", $sUrl, $postfield, array("Accept: application/json")); - } - - function sendCurlRequest($sMethod, $sUrl, $aParams=array(), $aHeaders=array()){ - - $this->aLastCurlRequestInfo = ''; - // - $ch = curl_init(); - $sType = strtoupper($sMethod); - // Force la méthode de requête utilisée (GET, POST...). - curl_setopt($ch, CURLOPT_CUSTOMREQUEST, $sType); - // Url à utiliser. - if (($sType == 'GET' || $sType == 'DELETE') && !empty($aParams)) - $sUrl .= '?' . http_build_query($aParams); - curl_setopt($ch, CURLOPT_URL, $sUrl); - // ajout des en-tête - curl_setopt($ch, CURLOPT_HTTPHEADER, $aHeaders); - // Retour sous forme de texte. - curl_setopt($ch, CURLOPT_RETURNTRANSFER, true); - // Requête POST PUT parameters. - - if ($sType == 'POST' || $sType == 'PUT') { - if($sType == 'POST'){ - curl_setopt($ch, CURLOPT_POST, true); - } - // Chaîne de requête en encodage URL. - //if (is_array($aParamsaParams) && !$bMultipartFormData) - // $aParams = http_build_query($aParams); - // Données de la requête. - curl_setopt($ch, CURLOPT_POSTFIELDS, $aParams); - // - //curl_setopt($ch, CURLOPT_SAFE_UPLOAD, true); - // Entête pour la requête en POST. - //$aHeaders[] = 'Content-Type: application/x-www-form-urlencoded'; - } - - curl_setopt($ch, CURLINFO_HEADER_OUT, true); - curl_setopt($ch, CURLOPT_HTTP_VERSION, CURL_HTTP_VERSION_1_1); - // Curl error: SSL certificate problem: unable to get local issuer certificate - // Curl error n°60 - curl_setopt ($ch, CURLOPT_SSL_VERIFYPEER, false); - curl_setopt($ch, CURLOPT_SSL_VERIFYHOST, false); - // - $output = curl_exec($ch); - // Erreur de la requête CURL. - if(curl_errno($ch)) { - writeToErrorLog('Curl error: ' . curl_error($ch)); - writeToErrorLog('Curl error n°' . curl_errno($ch)); - } - // Informations de la requête. - $aCurlInfo = curl_getinfo($ch); - $this->aLastCurlRequestInfo = $aCurlInfo; - - // Ferme la session CURL. - curl_close($ch); - return $output; - } - - function contactCurrentApi($sMethod, $sUrlPath, $aParams=array(), $sMode="json", $aAuthParams = null){ - - if($this->aProperties['web_server_name'] === "[HTTP_HOST]"){ - $this->aProperties['web_server_name'] = "https://localhost"; - } - - $sRestUrl = $this->aProperties['web_server_name'] . '/' . $this->aProperties['services_alias']; - - $this->contactAnotherApi($sMethod, $sRestUrl, $sUrlPath, $aParams, $sMode, $aAuthParams); + return curl_exec($ch); } - function contactAnotherApi($sMethod, $sRestUrl, $sUrlPath, $aParams=array(), $sMode="json", $aAuthParams = null){ - $mToken = $this->getToken($sRestUrl, $aAuthParams); - - $sUrl = $sRestUrl . "/" . $sUrlPath; - - if($mToken !== false){ - - // modification des paramètres si besoin - $aSendParams = array(); - $aHeaders = array("token: " . $mToken); - - switch ($sMode) { - case 'json': - $aSendParams = json_encode($aParams); - $aHeaders[] = "Content-Type: application/json"; - $aHeaders[] = "Accept: application/json"; - break; - case 'query': - $sUrl .= '?' . http_build_query($aParams); - $aHeaders[] = "Accept: application/x-vm-json"; - break; - case 'urlencode': - $aSendParams = http_build_query($aParams); - $aHeaders[] = "Accept: application/x-www-form-urlencoded"; - break; - case 'formdata' : - $aSendParams = $aParams; - break; - } - - $sOutput = $this->sendCurlRequest($sMethod, $sUrl, $aSendParams, $aHeaders); - error_log(print_r($this->aLastCurlRequestInfo, true)); - return $sOutput; - } else { - writeToErrorLog("This user can't have a token on Calimap at URL : " . $sRestUrl); - return false; - } - } - - /********************************************************************** - Sauve l'historique deprecated - **********************************************************************/ - function saveHistory() { - $aHistoryValues = array('bo_id' => $this->aValues["my_vitis_id"], 'login' => $_SESSION['ses_Login'], 'comment' => $this->status, 'date' => date('Y-m-d H:i:s')); - $this->oBd->insert($this->aTableInfo['schema_name'], 'history', $aHistoryValues, $this->aTableInfo['schema_name'] . '.history_history_id_seq', 'history_id'); - } - /********************************************************************** - Sauve une note ou commentaire (history sert d'historique) - **********************************************************************/ - function addHistoryLine($sComment, $sHistoryTable, $iBoId){ - $sUser = 'u_scheduler'; - if(isset($_SESSION['ses_Login']) && !empty($_SESSION['ses_Login'])){ - $sUser = $_SESSION['ses_Login']; - } - - $aHistoryValues = array('bo_id' => $iBoId, 'login' => $sUser, 'comment' => $sComment, 'date' => date('Y-m-d H:i:s')); - $this->oBd->insert($this->aTableInfo['schema_name'], $sHistoryTable, $aHistoryValues, $this->aTableInfo['schema_name'] . '.seq_' . $sHistoryTable . "_id" , 'history_id'); - } - - function commitNoteLine($sNoteLineField, $sNoteTable, $sBoTable, $sFieldId, $iBoId){ - // get note line - $aFields = $this->wabGetObject($this->aTableInfo['schema_name'], $sBoTable, $sFieldId, $iBoId); - - if(!empty($aFields[$sNoteLineField])){ - $sUser = 'u_scheduler'; - if(isset($_SESSION['ses_Login']) && !empty($_SESSION['ses_Login'])){ - $sUser = $_SESSION['ses_Login']; - } - $aNoteValues = array('bo_id' => $iBoId, 'login' => $sUser, 'comment' => $aFields[$sNoteLineField], 'date' => date('Y-m-d H:i:s')); - $this->oBd->insert($this->aTableInfo['schema_name'], $sNoteTable, $aNoteValues, $this->aTableInfo['schema_name'] . '.seq_' . $sNoteTable . "_id", 'history_id'); - } - - // reset note line - $this->aValues[$sNoteLineField] = ""; - $this->save(); - } - } ?> diff --git a/src/vitis/vas/rest/class/wab_lib/BusinessObject.class.sql.inc b/src/vitis/vas/rest/class/wab_lib/BusinessObject.class.sql.inc index a18ed1f2df0594917c4cdf5ec15499b422dd2273..bf02e36db648547116d594e3689cc070a8d36fc8 100755 --- a/src/vitis/vas/rest/class/wab_lib/BusinessObject.class.sql.inc +++ b/src/vitis/vas/rest/class/wab_lib/BusinessObject.class.sql.inc @@ -1,6 +1,5 @@ <?php $aSQL["getStatusId"] = 'SELECT * FROM [SCHEMA].rt_[TABLE]_status WHERE name = [STATUS_NAME]'; - $aSQL["getBoValues"] = 'SELECT * FROM [SCHEMA].[TABLE] WHERE [TABLE].[BOIDFIELD]=[BOID]'; - $aSQL["updateStatus"] = 'UPDATE [SCHEMA].[TABLE] SET status_id=[STATUS_ID] WHERE [TABLE].[BOIDFIELD]=[BOID]'; + $aSQL["updateStatus"] = 'UPDATE [SCHEMA].v_[TABLE] SET status_id=[STATUS_ID] WHERE v_[TABLE].[BOIDFIELD]=[BOID]'; $aSQL["getStatusName"] = 'SELECT name FROM [SCHEMA].rt_[TABLE]_status WHERE status_id = (SELECT status_id FROM [SCHEMA].[TABLE] WHERE [TABLE].[BOIDFIELD]=[BOID])'; ?> \ No newline at end of file diff --git a/src/vitis/vas/rest/conf/properties.inc b/src/vitis/vas/rest/conf/properties.inc old mode 100755 new mode 100644 diff --git a/src/vitis/vas/rest/conf/selected_properties.inc b/src/vitis/vas/rest/conf/selected_properties.inc old mode 100755 new mode 100644 diff --git a/src/vitis/vas/rest/ws/vitis/Exploitations.class.inc b/src/vitis/vas/rest/ws/vitis/Exploitations.class.inc new file mode 100755 index 0000000000000000000000000000000000000000..1703c2ce5b6eed19237293c8444271e3d0e4a709 --- /dev/null +++ b/src/vitis/vas/rest/ws/vitis/Exploitations.class.inc @@ -0,0 +1,362 @@ +<?php + +/** + * \file Exploitations.class.inc + * \class Exploitations + * + * \author Yoann Perollet <yoann.perollet@veremes.com>. + * + * \brief This file contains the Exploitations php class + * + * This class defines Rest Api to Vitis exploitations + * + */ +require_once 'Vitis.class.inc'; +require_once __DIR__ . '/../../class/vitis_lib/Connection.class.inc'; +require_once(__DIR__ . '/../../class/vmlib/BdDataAccess.inc'); + +class Exploitations extends Vitis { + /** + * @SWG\Definition( + * definition="/exploitations", + * allOf={ + * @SWG\Schema(ref="#/definitions/exploitations") + * } + * ) + * * @SWG\Tag( + * name="Exploitations", + * description="Operations about Exploitations" + * ) + */ + + /** + * construct + * @param type $aPath url of the request + * @param type $aValues parameters of the request + * @param type $properties properties + * @param type $bShortcut false to reinit variables + * @param type $oConnection connection object + */ + function __construct($aPath, $aValues, $properties, $bShortcut = false, $oConnection = false) { + parent::__construct($aPath, $aValues, $properties, $bShortcut, $oConnection); + $this->aSelectedFields = Array(); + } + + /** + * @SWG\Get(path="/exploitations/SharedDirectory", + * tags={"Exploitations"}, + * summary="Get shared directory tree", + * description="Request to get the shared directory tree", + * operationId="GET", + * produces={"application/json", "application/x-vm-json"}, + * @SWG\Parameter( + * name="token", + * in="query", + * description="user token", + * required=true, + * type="string" + * ), + * @SWG\Response( + * response=200, + * description="Poprerties Response", + * @SWG\Schema(ref="#/definitions/exploitations") + * ) + * ) + */ + + /** + * get Exploitations + * @return Exploitations + */ + function GET() { + // Arborescence du répertoire partagé. + if (strtolower($this->aPath[2]) == 'shareddirectory') { + $aTreeview = $this->getDirectoryTree($this->aProperties['shared_dir']); + if (!empty($aTreeview["data"][0]["nodes"])) + $this->aFields['tree']['data'] = $aTreeview["data"][0]["nodes"]; + else + $this->aFields['tree']['data'] = []; + } + // + $aXmlRacineAttribute['status'] = 1; + $sMessage = $this->asDocument('', 'vitis', $this->aValues['sEncoding'], True, $aXmlRacineAttribute, $this->aValues['sSourceEncoding'], $this->aValues['output']); + return $sMessage; + } + + /** + * Get directory tree. + */ + function getDirectoryTree($sDirectoryPath) { + $aReturn = array('status' => 1, 'message' => ''); + // Création de l'arborescence des fichiers du répertoire. + if (!empty($sDirectoryPath)) { + $sDirectoryName = 'Downloads'; + if (is_string($sDirectoryPath)) { + if (is_dir($sDirectoryPath)) { + $aDirStructure = $this->getDirStructure($sDirectoryPath, $sDirectoryName, $sDirectoryName, ""); + $aTreeview["data"][] = $aDirStructure["data"]; + if (!empty($aDirStructure["files"])) { + foreach ($aDirStructure["files"] as $aFiles) { + $aTreeview["files"][] = $aFiles; + } + } + } else + writeToErrorLog('scandir(' . $sDirectoryPath . '): failed to open dir'); + } + } + return $aTreeview; + } + + /* + * Retourne l'arborescence d'un répertoire formaté pour "bootstrap-treeview". + */ + + function getDirStructure($sDirectoryPath, $sSubDirectoryName, $sDirectoryName, $sFolder) { + $aFilteredDir['data'] = array('text' => $sSubDirectoryName, 'selectable' => true, 'path' => $sFolder . '/' . $sSubDirectoryName); + $aDir = scandir($sDirectoryPath); + // Les répertoires sont affichés avant les fichiers (idem windows). + $aSortedDir = array(); + $aSortedFiles = array(); + foreach ($aDir as $sName) { + $sPath = $sDirectoryPath . '/' . $sName; + $sFileType = filetype($sPath); + if ($sFileType == 'dir') + $aSortedDir[] = $sName; + else + $aSortedFiles[] = $sName; + } + sort($aSortedDir, SORT_STRING|SORT_FLAG_CASE); + sort($aSortedFiles, SORT_STRING|SORT_FLAG_CASE); + $aDir = array_merge($aSortedDir, $aSortedFiles); + // + if ($sSubDirectoryName !== $sDirectoryName) + $sFolder .= '/' . $sSubDirectoryName; + + foreach ($aDir as $sName) { + $sPath = $sDirectoryPath . '/' . $sName; + $sFileType = filetype($sPath); + // Répertoire ? + if ($sFileType == 'dir') { + if ($sName != '.' && $sName != '..') { + if (is_dir($sPath)) { + $aDirStructure = $this->getDirStructure($sPath . '/', $sName, $sDirectoryName, $sFolder); + //if (!empty($aDirStructure['data']['nodes'])) { + // Structure du répertoire. + $aFilteredDir['data']['nodes'][] = $aDirStructure['data']; + // Liste des fichiers du répertoire. + if (!empty($aDirStructure["files"])) { + foreach ($aDirStructure["files"] as $aFiles) { + $aFilteredDir["files"][] = $aFiles; + } + } + //} + } else + writeToErrorLog('scandir(' . $sPath . '): failed to open dir'); + } + } + // fichier ? + if ($sFileType == 'file') { + // Taille + unité du fichier. + //$iFileSize = filesize($sPath); + $aFileInfos = stat($sPath); + $iFileSizeLabel = $aFileInfos['size']; + $aFileSizeUnity = array('o', 'Ko', 'Mo', 'Go', 'To'); + $i = 0; + while ($iFileSizeLabel > 1024) { + $iFileSizeLabel /= 1024; + $i++; + } + // Sauve la structure du fichier pour le treeview. + $sFileLabel = $sName . ' (' . round($iFileSizeLabel) . ' ' . $aFileSizeUnity[$i] . ')'; + $aFilteredDir['data']['nodes'][] = array( + 'folder' => $sFolder, + 'directory' => $sDirectoryName, + 'name' => $sName, + 'text' => $sFileLabel, + 'icon' => 'glyphicon glyphicon-file', + 'path' => str_replace('//', '/', $sFolder . '/' . '/' . $sName), + //'tags' => array('<span class="glyphicon glyphicon-trash"></span>'), + 'size' => $aFileInfos['size'], + 'selectable' => false + ); + // Sauve le nom et la date du fichier. + $aFilteredDir['files'][] = array( + 'path' => str_replace('//', '/', $sFolder . '/' . '/' . $sName), + //'last_modif' => floor((time() - $aFileInfos['mtime']) / (24 * 3600)) // dernière modif. (Nb jours). + ); + } + } + return $aFilteredDir; + } + + /** + * @SWG\Post(path="/exploitations/SharedDirectory/Directory", + * tags={"Exploitations"}, + * summary="Create directory", + * description="Request to create a directory", + * operationId="POST", + * produces={"application/xml", "application/json"}, + * @SWG\Parameter( + * name="token", + * in="formData", + * description="user token", + * required=true, + * type="string" + * ), + * @SWG\Parameter( + * name="directory_path", + * in="formData", + * description="path of the directory", + * required=true, + * type="string" + * ), + * @SWG\Response( + * response=200, + * description="Poprerties Response", + * @SWG\Schema(ref="#/definitions/exploitations/SharedDirectory") + * ) + * ) + */ + + /** + * @SWG\Post(path="/exploitations/SharedDirectory/File", + * tags={"Exploitations"}, + * summary="Ulpload file", + * description="Request to upload a file", + * operationId="POST", + * produces={"application/xml", "application/json"}, + * @SWG\Parameter( + * name="token", + * in="formData", + * description="user token", + * required=true, + * type="string" + * ), + * @SWG\Parameter( + * name="directory_path", + * in="formData", + * description="path of the directory", + * required=true, + * type="string" + * ), + * @SWG\Response( + * response=200, + * description="Poprerties Response", + * @SWG\Schema(ref="#/definitions/exploitations/SharedDirectory") + * ) + * ) + */ + + /** + * insert user + * @return id of the user created + */ + function POST() { + // Répertoire partagé. + if (strtolower($this->aPath[2]) == 'shareddirectory') { + // Création d'un répertoire. + if (strtolower($this->aPath[3]) == 'directory') { + if (!empty($this->aValues['directory_path'])) { + if (mkdir($this->aProperties['shared_dir'] . '/' . $this->aValues['directory_path'])) { + $aXmlRacineAttribute['status'] = 1; + $sMessage = $this->asDocument('', 'vitis', $this->aValues['sEncoding'], True, $aXmlRacineAttribute, $this->aValues['sSourceEncoding'], $this->aValues['output']); + } + else { + $oError = new VitisError(1, 'DIRECTORY_CREATION_ERROR_EXPLOITATION_EXPLOITATION'); + $sMessage = $oError->asDocument('', 'vitis', $this->aValues['sEncoding'], True, $aXmlRacineAttribute, $this->aValues['sSourceEncoding'], $this->aValues['output']); + } + } + } + // Upload d'un fichier. + else if (strtolower($this->aPath[3]) == 'file') { + if (!empty($_FILES["file"])) { + if (!empty($this->aValues['directory_path'])) + $sFilePath = $this->aProperties['shared_dir'] . '/' . $this->aValues['directory_path'] . '/' . $_FILES["file"]["name"]; + else + $sFilePath = $this->aProperties['shared_dir'] . '/' . $_FILES["file"]["name"]; + if (!move_uploaded_file($_FILES['file']['tmp_name'], $sFilePath)) { + $oError = new VitisError(1, 'FILE_CREATION_ERROR_EXPLOITATION_EXPLOITATION'); + $sMessage = $oError->asDocument('', 'vitis', $this->aValues['sEncoding'], True, $aXmlRacineAttribute, $this->aValues['sSourceEncoding'], $this->aValues['output']); + } + else { + $aXmlRacineAttribute['status'] = 1; + $sMessage = $this->asDocument('', 'vitis', $this->aValues['sEncoding'], True, $aXmlRacineAttribute, $this->aValues['sSourceEncoding'], $this->aValues['output']); + } + } + } + } + return $sMessage; + } + + /** + * @SWG\Delete(path="/exploitations/SharedDirectory", + * tags={"Exploitations"}, + * summary="delete shared directory files", + * description="Request to delete shared directory files", + * operationId="DELETE", + * produces={"application/json", "application/x-vm-json"}, + * @SWG\Parameter( + * name="token", + * in="query", + * description="user token", + * required=true, + * type="string" + * ), + * * @SWG\Parameter( + * name="idList", + * in="query", + * description="path of the files", + * required=true, + * type="string" + * ), + * @SWG\Response( + * response=200, + * description="Poprerties Response", + * @SWG\Schema(ref="#/definitions/exploitations/SharedDirectory") + * ) + * ) + */ + + /** + * delete exploitation files + */ + function DELETE() { + // Verify connection. + if (!empty($this->oConnection->oError)) { + $oError = $this->oConnection->oError; + $aXmlRacineAttribute['status'] = 0; + $sMessage = $oError->asDocument('', 'vitis', $this->aValues['sEncoding'], True, $aXmlRacineAttribute, $this->aValues['sSourceEncoding'], $this->aValues['output']); + return $sMessage; + } + // Privilège "vitis_admin" requis. + if (!in_array('vitis_admin', $this->oConnection->aPrivileges)) { + $oError = new VitisError(1, "Rights problem : you don't have right to delete shared directory files"); + $aXmlRacineAttribute['status'] = 0; + $sMessage = $oError->asDocument('', 'vitis', $this->aValues['sEncoding'], True, $aXmlRacineAttribute, $this->aValues['sSourceEncoding'], $this->aValues['output']); + return $sMessage; + } + // Suppression des fichiers. + $aXmlRacineAttribute['status'] = 1; + $sMessage = $this->asDocument('', 'vitis', $this->aValues['sEncoding'], True, $aXmlRacineAttribute, $this->aValues['sSourceEncoding'], $this->aValues['output']); + if (!empty($this->aValues['idList'])) { + $aPathsToDelete = explode('|', $this->aValues['idList']); + $aDirToDelete = array(); + foreach ($aPathsToDelete as $sPath) { + $sPath = str_replace('//', '/', $this->aProperties['shared_dir'] . $sPath); + if (file_exists($sPath)) { + if (is_dir($sPath)) + array_unshift($aDirToDelete, $sPath); + else + unlink($sPath); + } + } + } + // Suppression des répertoires. + foreach ($aDirToDelete as $sPath) { + rmdir($sPath); + } + // + return $sMessage; + } +} +?> \ No newline at end of file diff --git a/src/vitis/vas/rest/ws/vitis/GenericQuerys.class.inc b/src/vitis/vas/rest/ws/vitis/GenericQuerys.class.inc old mode 100755 new mode 100644 diff --git a/src/vitis/vas/rest/ws/vitis/Modes.class.inc b/src/vitis/vas/rest/ws/vitis/Modes.class.inc old mode 100755 new mode 100644 index f9754ec0d4f3c9291507b34474333f70bcac1b52..c838ebe1c37627b79b3783a89d8f601904e94653 --- a/src/vitis/vas/rest/ws/vitis/Modes.class.inc +++ b/src/vitis/vas/rest/ws/vitis/Modes.class.inc @@ -34,8 +34,8 @@ class Modes extends Vitis { * construct * @param type $aPath url of the request * @param type $aValues parameters of the request - * @param type $properties properties - * @param type $bShortcut false to reinit variables + * @param type $properties properties + * @param type $bShortcut false to reinit variables * @param type $oConnection connection object */ function __construct($aPath, $aValues, $properties, $bShortcut = false, $oConnection = false) { @@ -131,6 +131,11 @@ class Modes extends Vitis { */ function GET() { if ($this->oConnection->oError == null) { + if (!empty($this->aProperties["public_token"]) && $this->aProperties["allow_public_connection"] === true){ + if($this->aProperties["public_token"] === $this->aValues['token']){ + $this->aValues["filter"] = '{"relation": "AND","operators":[{"column": "mode_id","compare_operator": "<>","value": "user"}]}'; + } + } if (isset($this->aValues['action']) && !empty($this->aValues['action'])) { if ($this->aValues['action'] == 'getAll') { $aReturn = $this->genericGet($this->aProperties['schema_framework'], "vm_mode_rolname", "mode_id", true); diff --git a/src/vitis/vas/rest/ws/vitis/PrivateToken.class.inc b/src/vitis/vas/rest/ws/vitis/PrivateToken.class.inc index 649dc10c0bc7100d38721af81cab49b19706eab2..8295dcb302800b3391b9833d953d442b1070f955 100644 --- a/src/vitis/vas/rest/ws/vitis/PrivateToken.class.inc +++ b/src/vitis/vas/rest/ws/vitis/PrivateToken.class.inc @@ -134,76 +134,85 @@ class PrivateToken extends Vitis { } if (!$bXMLError) { - //connect to database - $oBd = new BD($this->aValues["user"], $this->aValues["password"], $this->aProperties["database"], $this->aProperties["server"], $this->aProperties["port"], $this->aProperties["sgbd"], $this->aProperties["page_encoding"]); - $_SESSION["ses_Login"] = $this->aValues["user"]; - $ciphertext = stringToHex(des($this->aValues["user"], $this->aValues["password"], 1, 0)); - $_SESSION["ses_Password"] = $ciphertext; - $_SESSION["ses_Remember"] = false; - $_SESSION["ses_Date"] = date('Y-m-d H:i:s', time() + ($this->aValues['duration'] * 60)); - if ($oBd->erreurRencontree) { - $oError = new VitisError(1, $oBd->sMessage); + // Teste si la base de données est joignable. + if (fsockopen($this->aProperties["server"], $this->aProperties["port"], $errno, $errstr) === false) { + $oError = new VitisError(19, "The database is unreachable"); $aXmlRacineAttribute['status'] = 0; $sMessage = $oError->asDocument('', 'vitis', $this->aValues['sEncoding'], True, $aXmlRacineAttribute, $this->aValues['sSourceEncoding'], $this->aValues['output']); - $bXMLError = true; - } else { - // Privilège 'vitis_user' obligatoire. - $aParams['sLogin'] = array('value' => $this->aValues["user"], 'type' => 'string'); - $oPDOresult = $oBd->executeWithParams($aSql['getUserConnectionPrivileges'], $aParams); - if ($oBd->nombreLigne($oPDOresult) == 0) { - $oError = new VitisError(18, "No 'vitis_user' privilege."); + writeToErrorLog("ERROR : " . $errstr . ' ' . $this->aValues["user"] . "'."); + } + else { + //connect to database + $oBd = new BD($this->aValues["user"], $this->aValues["password"], $this->aProperties["database"], $this->aProperties["server"], $this->aProperties["port"], $this->aProperties["sgbd"], $this->aProperties["page_encoding"]); + $_SESSION["ses_Login"] = $this->aValues["user"]; + $ciphertext = stringToHex(des($this->aValues["user"], $this->aValues["password"], 1, 0)); + $_SESSION["ses_Password"] = $ciphertext; + $_SESSION["ses_Remember"] = false; + $_SESSION["ses_Date"] = date('Y-m-d H:i:s', time() + ($this->aValues['duration'] * 60)); + if ($oBd->erreurRencontree) { + $oError = new VitisError(1, $oBd->sMessage); $aXmlRacineAttribute['status'] = 0; $sMessage = $oError->asDocument('', 'vitis', $this->aValues['sEncoding'], True, $aXmlRacineAttribute, $this->aValues['sSourceEncoding'], $this->aValues['output']); - writeToErrorLog("ERROR : No 'vitis_user' privilege for user '" . $this->aValues["user"] . "'."); + $bXMLError = true; } else { - // L'utilisateur doit exister dans la table s_vitis.user - $aParams['sSchemaFramework'] = array('value' => $this->aProperties['schema_framework'], 'type' => 'schema_name'); - $aParams['sLogin'] = array('value' => $_SESSION["ses_Login"], 'type' => 'string'); - $oPDOresult = $oBd->executeWithParams($aSql['checkUser'], $aParams); + // Privilège 'vitis_user' obligatoire. + $aParams['sLogin'] = array('value' => $this->aValues["user"], 'type' => 'string'); + $oPDOresult = $oBd->executeWithParams($aSql['getUserConnectionPrivileges'], $aParams); if ($oBd->nombreLigne($oPDOresult) == 0) { - $oError = new VitisError(1, 'The user ' . $_SESSION["ses_Login"] . ' does not exist'); + $oError = new VitisError(18, "No 'vitis_user' privilege."); $aXmlRacineAttribute['status'] = 0; $sMessage = $oError->asDocument('', 'vitis', $this->aValues['sEncoding'], True, $aXmlRacineAttribute, $this->aValues['sSourceEncoding'], $this->aValues['output']); - writeToErrorLog('ERROR : The user ' . $_SESSION["ses_Login"] . ' does not exist.'); + writeToErrorLog("ERROR : No 'vitis_user' privilege for user '" . $this->aValues["user"] . "'."); } else { - //verify the ip from wich the user is connected - $aParams = array(); + // L'utilisateur doit exister dans la table s_vitis.user $aParams['sSchemaFramework'] = array('value' => $this->aProperties['schema_framework'], 'type' => 'schema_name'); $aParams['sLogin'] = array('value' => $_SESSION["ses_Login"], 'type' => 'string'); - $oPDOresult = $oBd->executeWithParams($aSql['checkIP'], $aParams); - $aFields = $oBd->ligneSuivante($oPDOresult); - $oMetadataAccess = new MetadataAccess($oBd, $_SESSION["ses_Login"], $_SESSION["ses_Password"], session_id(), $this->aProperties); - $bAuthorizedIp = $oMetadataAccess->checkUserIp($_SERVER['REMOTE_ADDR']); - if (!$bAuthorizedIp) { - $oError = new VitisError(11, 'Connection to the database forbidden with the ip \'' . $_SERVER['REMOTE_ADDR'] . '\'.'); + $oPDOresult = $oBd->executeWithParams($aSql['checkUser'], $aParams); + if ($oBd->nombreLigne($oPDOresult) == 0) { + $oError = new VitisError(1, 'The user ' . $_SESSION["ses_Login"] . ' does not exist'); $aXmlRacineAttribute['status'] = 0; $sMessage = $oError->asDocument('', 'vitis', $this->aValues['sEncoding'], True, $aXmlRacineAttribute, $this->aValues['sSourceEncoding'], $this->aValues['output']); - $bXMLError = true; - writeToErrorLog('ERROR : Connection to the database forbidden with the ip \'' . $_SERVER['REMOTE_ADDR'] . '\'.'); + writeToErrorLog('ERROR : The user ' . $_SESSION["ses_Login"] . ' does not exist.'); } else { + //verify the ip from wich the user is connected + $aParams = array(); + $aParams['sSchemaFramework'] = array('value' => $this->aProperties['schema_framework'], 'type' => 'schema_name'); + $aParams['sLogin'] = array('value' => $_SESSION["ses_Login"], 'type' => 'string'); + $oPDOresult = $oBd->executeWithParams($aSql['checkIP'], $aParams); + $aFields = $oBd->ligneSuivante($oPDOresult); + $oMetadataAccess = new MetadataAccess($oBd, $_SESSION["ses_Login"], $_SESSION["ses_Password"], session_id(), $this->aProperties); + $bAuthorizedIp = $oMetadataAccess->checkUserIp($_SERVER['REMOTE_ADDR']); + if (!$bAuthorizedIp) { + $oError = new VitisError(11, 'Connection to the database forbidden with the ip \'' . $_SERVER['REMOTE_ADDR'] . '\'.'); + $aXmlRacineAttribute['status'] = 0; + $sMessage = $oError->asDocument('', 'vitis', $this->aValues['sEncoding'], True, $aXmlRacineAttribute, $this->aValues['sSourceEncoding'], $this->aValues['output']); + $bXMLError = true; + writeToErrorLog('ERROR : Connection to the database forbidden with the ip \'' . $_SERVER['REMOTE_ADDR'] . '\'.'); + } else { - error_log('session_id():' . session_id()); + error_log('session_id():' . session_id()); - $oConnection = new Connection(Array('token' => session_id()), $this->aProperties); - $this->aFields['token'] = session_id(); - $this->aFields['user'] = $_SESSION["ses_Login"]; - $this->aFields['validity_date'] = date('Y-m-d H:i:s', time() + ($this->aValues['duration'] * 60)); - $this->aFields['user_id'] = $aFields['user_id']; - $this->aFields['privileges'] = $oConnection->aPrivileges; - if ($this->aValues['output'] === 'application/xml') { - $this->aFields['privileges'] = implode(',', $this->aFields['privileges']); + $oConnection = new Connection(Array('token' => session_id()), $this->aProperties); + $this->aFields['token'] = session_id(); + $this->aFields['user'] = $_SESSION["ses_Login"]; + $this->aFields['validity_date'] = date('Y-m-d H:i:s', time() + ($this->aValues['duration'] * 60)); + $this->aFields['user_id'] = $aFields['user_id']; + $this->aFields['privileges'] = $oConnection->aPrivileges; + if ($this->aValues['output'] === 'application/xml') { + $this->aFields['privileges'] = implode(',', $this->aFields['privileges']); + } + $_SESSION["ses_user_id"] = $aFields['user_id']; + $_SESSION["ses_restriction"] = $aFields['restriction']; + $aXmlRacineAttribute['status'] = 1; + $aParams = array(); + $aParams['sSchemaFramework'] = array('value' => $this->aProperties['schema_framework'], 'type' => 'schema_name'); + $aParams['user_id'] = array('value' => $aFields['user_id'], 'type' => 'number'); + $aParams['date'] = array('value' => gmdate('Y-m-d H:i:s'), 'type' => 'string'); + $oPDOresult = $oBd->executeWithParams($aSql['updateLastConnection'], $aParams); + $sLogString = "connection" . $this->aProperties["log_delim"] . $_SESSION["ses_Login"] . $this->aProperties["log_delim"] . session_id(); + writeToLog($sLogString, $this->aProperties["connexion_log_file"]); + $sMessage = $this->asDocument('', 'vitis', $this->aValues['sEncoding'], True, $aXmlRacineAttribute, $this->aValues['sSourceEncoding'], $this->aValues['output']); } - $_SESSION["ses_user_id"] = $aFields['user_id']; - $_SESSION["ses_restriction"] = $aFields['restriction']; - $aXmlRacineAttribute['status'] = 1; - $aParams = array(); - $aParams['sSchemaFramework'] = array('value' => $this->aProperties['schema_framework'], 'type' => 'schema_name'); - $aParams['user_id'] = array('value' => $aFields['user_id'], 'type' => 'number'); - $aParams['date'] = array('value' => gmdate('Y-m-d H:i:s'), 'type' => 'string'); - $oPDOresult = $oBd->executeWithParams($aSql['updateLastConnection'], $aParams); - $sLogString = "connection" . $this->aProperties["log_delim"] . $_SESSION["ses_Login"] . $this->aProperties["log_delim"] . session_id(); - writeToLog($sLogString, $this->aProperties["connexion_log_file"]); - $sMessage = $this->asDocument('', 'vitis', $this->aValues['sEncoding'], True, $aXmlRacineAttribute, $this->aValues['sSourceEncoding'], $this->aValues['output']); } } } diff --git a/src/vitis/vas/rest/ws/vitis/Vitis.class.inc b/src/vitis/vas/rest/ws/vitis/Vitis.class.inc old mode 100755 new mode 100644 diff --git a/src/vitis/vas/rest/ws/vitis/VitisSection.class.inc b/src/vitis/vas/rest/ws/vitis/VitisSection.class.inc index cd1e1840875aac99b320e6738dbeeb319528b0d4..1328958b8b1cf354a4bfa83ad2e96c06d3d89afb 100755 --- a/src/vitis/vas/rest/ws/vitis/VitisSection.class.inc +++ b/src/vitis/vas/rest/ws/vitis/VitisSection.class.inc @@ -30,7 +30,7 @@ class VitisSection extends Vitis { */ function __construct($aPath, $aValues, $properties, $bShortcut = false, $oConnection = false) { parent::__construct($aPath, $aValues, $properties, $bShortcut, $oConnection); - $this->aSelectedFields = Array("section_id", "tab_id", "event", "index", "label", "name", "link_table_name", "template", "ressource_id"); + $this->aSelectedFields = Array("section_id", "tab_id", "event", "index", "label", "name", "link_table_name", "template", "ressource_id", "module_name"); } /** diff --git a/src/vitis/vas/rest/ws/vitis/VitisSections.class.inc b/src/vitis/vas/rest/ws/vitis/VitisSections.class.inc index fb91cfe1ed733f0a04683f7921e7db9b9cf13dd0..3e7710cee087f81790610a140527bf029d79887e 100755 --- a/src/vitis/vas/rest/ws/vitis/VitisSections.class.inc +++ b/src/vitis/vas/rest/ws/vitis/VitisSections.class.inc @@ -45,7 +45,7 @@ class VitisSections extends Vitis { */ function __construct($aPath, $aValues, $properties, $bShortcut = false, $oConnection = false) { parent::__construct($aPath, $aValues, $properties, $bShortcut, $oConnection); - $this->aSelectedFields = Array("section_id", "tab_id", "event", "index", "label", "name", "link_table_name", "template", "ressource_id", "tab_name", "mode_id"); + $this->aSelectedFields = Array("section_id", "tab_id", "event", "index", "label", "name", "link_table_name", "template", "ressource_id", "tab_name", "mode_id", "module_name"); } /** diff --git a/src/vitis/vas/sql/sqlQueries.xml b/src/vitis/vas/sql/sqlQueries.xml old mode 100755 new mode 100644