diff --git a/Makefile b/Makefile index 3b084dd50b5b..1cd8a55aaca1 100644 --- a/Makefile +++ b/Makefile @@ -242,7 +242,9 @@ gh-pages: .build/python-venv.timestamp --app 'Alternate mobile application' apps/mobile_alt.html 'An alternate mobile example application for GeoMapFish.' \ --app 'Alternate desktop application' apps/desktop_alt.html 'An alternate desktop example application for GeoMapFish.' \ --app 'Iframe api application' apps/iframe_api.html 'A desktop application for GeoMapFish without any tools that can be used within an iframe.' \ - --app 'Object editing editor' apps/oeedit.html 'An example application for editing an object.' \ + --app 'Object editing editor' \ + 'apps/oeedit.html?objectediting_geomtype=MultiPolygon&objectediting_id=Test&objectediting_layer=112&objectediting_theme=ObjectEditing&objectediting_property=name&tree_groups=ObjectEditing' \ + 'An example application for editing an object.' \ $< $(GMF_EXAMPLES_HTML_FILES) > $@ .build/test-check-example/%.check.timestamp: test/check-example/%.html \ diff --git a/contribs/gmf/src/backgroundlayerselector/component.js b/contribs/gmf/src/backgroundlayerselector/component.js index d9eb93e4c7bf..492a45f8187a 100644 --- a/contribs/gmf/src/backgroundlayerselector/component.js +++ b/contribs/gmf/src/backgroundlayerselector/component.js @@ -64,10 +64,14 @@ function gmfBackgroundlayerselectorTemplateUrl($element, $attrs, gmfBackgroundla * gmf-backgroundlayerselector-select="onBackgroundSelected()"> * * - * Used UI metadata: + * Used metadata: * * * thumbnail: The URL used for the icon. * + * Used functionnalities: + * + * * default_basemap: Base maps to use by default. + * * @htmlAttribute {import("ol/Map.js").default=} gmf-backgroundlayerselector-map The map. * @htmlAttribute {string} gmf-backgroundlayer-opacity-options The opacity slider options. * @htmlAttribute {Function} gmf-backgroundlayerselector-select Function called diff --git a/contribs/gmf/src/controllers/AbstractAppController.js b/contribs/gmf/src/controllers/AbstractAppController.js index 1fc6c7d49f09..6fc22279b118 100644 --- a/contribs/gmf/src/controllers/AbstractAppController.js +++ b/contribs/gmf/src/controllers/AbstractAppController.js @@ -36,6 +36,7 @@ import {ThemeEventType} from 'gmf/theme/Manager.js'; /** * A part of the application config. + * * @typedef {Object} Config * @property {number} srid * @property {import("ol/style/Style.js").default} [positionFeatureStyle] @@ -55,6 +56,12 @@ import {ThemeEventType} from 'gmf/theme/Manager.js'; * This file includes `goog.require` for base components/directives used * by the HTML page and the controller to provide the configuration. * + * Used functionnalities: + * + * * open_panel: When set, contains the name of the panel to open upon loading an application. + * Note: although this is a list, only one can be defined. + * + * * @param {Config} config A part of the application config. * @param {import('ol/Map.js').default} map The map. * @param {angular.IScope} $scope Scope. diff --git a/contribs/gmf/src/datasource/Manager.js b/contribs/gmf/src/datasource/Manager.js index 3fbcdc751e85..37e7f5e9337e 100644 --- a/contribs/gmf/src/datasource/Manager.js +++ b/contribs/gmf/src/datasource/Manager.js @@ -44,19 +44,22 @@ import olSourceTileWMS from 'ol/source/TileWMS.js'; /** - * @hidden + * The GeoMapFish DataSources Manager is responsible of listenening to the + * c2cgeoportal's themes to create instances of `ngeo.datasource.DataSource` + * objects with the layer definitions found and push them in the + * `DataSources` collection. The Manager must be initialized + * with the app's map using the setDatasourcseMap() method. + * + * When changing theme, these data sources are cleared then re-created. + * + * Used metadata: + * + * * identifierAttributeField: The field used in the 'display query window' as feature title. + * For WMS layers. */ export class DatasourceManager { /** - * The GeoMapFish DataSources Manager is responsible of listenening to the - * c2cgeoportal's themes to create instances of `ngeo.datasource.DataSource` - * objects with the layer definitions found and push them in the - * `DataSources` collection. The Manager must be initialized - * with the app's map using the setDatasourcseMap() method. - * - * When changing theme, these data sources are cleared then re-created. - * * @param {angular.IQService} $q Angular q service * @param {angular.IScope} $rootScope Angular rootScope. * @param {angular.ITimeoutService} $timeout Angular timeout service. diff --git a/contribs/gmf/src/disclaimer/component.js b/contribs/gmf/src/disclaimer/component.js index 49d9fbc8f872..b1e01859c928 100644 --- a/contribs/gmf/src/disclaimer/component.js +++ b/contribs/gmf/src/disclaimer/component.js @@ -26,7 +26,6 @@ const module = angular.module('gmfDisclaimer', [ /** - * * @param {import("ol/layer/Base.js").default} layer Layer * @param {function(string):void} func Function */ @@ -39,9 +38,11 @@ function forEachDisclaimer(layer, func) { /** - * @constructor - * @private - * @hidden + * Used metadata: + * + * * disclaimer: The disclaimer text for this element. + * For WMS and WMTS layers, layer groups and themes. + * * @param {!JQuery} $element Element. * @param {!angular.ISCEService} $sce Angular sce service. * @param {!angular.ITimeoutService} $timeout Angular timeout service. @@ -51,10 +52,11 @@ function forEachDisclaimer(layer, func) { * @param {!import("ngeo/misc/EventHelper.js").EventHelper} ngeoEventHelper Ngeo Event Helper. * @param {!import("ngeo/map/LayerHelper.js").LayerHelper} ngeoLayerHelper Ngeo Layer Helper. * @ngInject + * @constructor * @ngdoc controller * @ngname GmfDisclaimerController */ -function Controller( +function DisclamerController( $element, $sce, $timeout, gettextCatalog, ngeoDisclaimer, ngeoEventHelper, ngeoLayerHelper ) { @@ -148,7 +150,7 @@ function Controller( /** * Initialise the controller. */ -Controller.prototype.$onInit = function() { +DisclamerController.prototype.$onInit = function() { if (!this.map) { throw new Error('Missing map'); } @@ -162,7 +164,7 @@ Controller.prototype.$onInit = function() { * @param {Event|import('ol/events/Event.js').default} evt Event. * @private */ -Controller.prototype.handleLayersAdd_ = function(evt) { +DisclamerController.prototype.handleLayersAdd_ = function(evt) { if (evt instanceof CollectionEvent) { this.timeout_(() => { const layer = evt.element; @@ -177,7 +179,7 @@ Controller.prototype.handleLayersAdd_ = function(evt) { * @param {Event|import('ol/events/Event.js').default} evt Event. * @private */ -Controller.prototype.handleLayersRemove_ = function(evt) { +DisclamerController.prototype.handleLayersRemove_ = function(evt) { if (evt instanceof CollectionEvent) { const layer = evt.element; console.assert(layer instanceof olLayerBase); @@ -190,7 +192,7 @@ Controller.prototype.handleLayersRemove_ = function(evt) { * @param {import("ol/layer/Base.js").default} layer Layer. * @private */ -Controller.prototype.registerLayer_ = function(layer) { +DisclamerController.prototype.registerLayer_ = function(layer) { const layerUid = olUtilGetUid(layer); @@ -258,7 +260,7 @@ Controller.prototype.registerLayer_ = function(layer) { * @param {import("ol/layer/Base.js").default} layer Layer. * @private */ -Controller.prototype.unregisterLayer_ = function(layer) { +DisclamerController.prototype.unregisterLayer_ = function(layer) { const layerUid = olUtilGetUid(layer); @@ -281,7 +283,7 @@ Controller.prototype.unregisterLayer_ = function(layer) { }; -Controller.prototype.$onDestroy = function() { +DisclamerController.prototype.$onDestroy = function() { if (!this.dataLayerGroup_) { throw new Error('Missing dataLayerGroup'); } @@ -293,7 +295,7 @@ Controller.prototype.$onDestroy = function() { * @param {string} msg Disclaimer message. * @private */ -Controller.prototype.showDisclaimerMessage_ = function(msg) { +DisclamerController.prototype.showDisclaimerMessage_ = function(msg) { msg = this.gettextCatalog_.getString(msg); if (this.external) { if (this.msgs_.indexOf(msg) < 0) { @@ -320,7 +322,7 @@ Controller.prototype.showDisclaimerMessage_ = function(msg) { * @param {string} msg Disclaimer message. * @private */ -Controller.prototype.closeDisclaimerMessage_ = function(msg) { +DisclamerController.prototype.closeDisclaimerMessage_ = function(msg) { msg = this.gettextCatalog_.getString(msg); if (this.external) { this.visibility = false; @@ -393,7 +395,7 @@ Controller.prototype.closeDisclaimerMessage_ = function(msg) { * @ngname gmfDisclaimer */ const disclaimerComponent = { - controller: Controller, + controller: DisclamerController, bindings: { 'layerVisibility': '} customRules * @property {Array.} directedRules */ + + module.component('gmfFilterselector', { bindings: { active: '=', map: '<', toolGroup: '<' }, - controller: Controller, + controller: FilterSelectorController, templateUrl: gmfFilterselectorTemplateUrl }); diff --git a/contribs/gmf/src/layertree/TreeManager.js b/contribs/gmf/src/layertree/TreeManager.js index aaf416bca080..b8d35f2f7ef5 100644 --- a/contribs/gmf/src/layertree/TreeManager.js +++ b/contribs/gmf/src/layertree/TreeManager.js @@ -30,6 +30,7 @@ import * as olEvents from 'ol/events.js'; * * This service's theme is a GmfTheme with only children and a name. * Thought to be the tree source of the gmf layertree directive. + * * @constructor * @param {angular.ITimeoutService} $timeout Angular timeout service. * @param {angular.auto.IInjectorService} $injector Angular injector service. diff --git a/contribs/gmf/src/layertree/component.js b/contribs/gmf/src/layertree/component.js index 223b4c4afd0c..d6b05ae07e40 100644 --- a/contribs/gmf/src/layertree/component.js +++ b/contribs/gmf/src/layertree/component.js @@ -136,7 +136,7 @@ function gmfLayertreeTemplate($element, $attrs, gmfLayertreeTemplate) { * metadata URLs in a new window. By default, and in the default template, * links will be opened in a popup (The window.openIframePopup function must be available !) * - * Used UI metadata: + * Used metadata: * * * isChecked: if 'false' the layer visibility will be set to false. * * iconUrl: layer icon full URL. @@ -144,6 +144,22 @@ function gmfLayertreeTemplate($element, $attrs, gmfLayertreeTemplate) { * * isLegendExpanded: if 'true' the legend is expanded by default. * * metadataUrl: Display a popup with the content of the given URL if * possible also open a new window. + * * exclusiveGroup: Whether the group contain children that have to be mutually + * exclusive, meaning that only one child may be ON at any time. + * * legend: Display the legend of this layers. For WMS and WMTS layers. + * * legendImage: The URL to the image used as a legend in the layer tree. For WMS and WMTS layers. + * * maxResolution: The max resolution where the layer is visible. For WMS layers. + * On WMTS layers it will have effect on the node in the layertree but not on the layertree directly. + * * minResolution: The min resolution where the layer is visible. For WMS layers. + * On WMTS layers it will have effect on the node in the layertree but not on the layer directly. + * * ogcServer: The corresponding OGC server for a WMTS layer. For WMTS layers. + * * opacity: Layer opacity. 1.0 means fuly visible, 0 means invisible, For WMS and WMTS layers. + * * timeAttribute: The name of the time attribute. For WMS(-T) layers. + * * wmsLayers: A corresponding WMS layer for a WMTS layers. Used to query the WMTS layers and to print it. + * (See also printLayers and queryLayers metadata for more granularity). For WMTS Layers. + * * printLayers: A WMS layer that will be used instead of the WMTS layers in the print. + * * queryLayers: The WMS layers used as references to query the WMTS layers. For WMTS layers. + * * isExpanded: Whether the layer group is expanded by default. For layer groups (only). * * @htmlAttribute {import("ol/Map.js").default} gmf-layertree-map The map. * @htmlAttribute {Object|undefined} gmf-layertree-dimensions Global dimensions object. diff --git a/contribs/gmf/src/objectediting/component.js b/contribs/gmf/src/objectediting/component.js index 33640e896fbb..9655bd6525ea 100644 --- a/contribs/gmf/src/objectediting/component.js +++ b/contribs/gmf/src/objectediting/component.js @@ -22,6 +22,14 @@ import {getUid as olUtilGetUid} from 'ol/util.js'; import olCollection from 'ol/Collection.js'; import * as olEvents from 'ol/events.js'; import olFormatGeoJSON from 'ol/format/GeoJSON.js'; +import Point from 'ol/geom/Point.js'; +import LineString from 'ol/geom/LineString.js'; +import LinearRing from 'ol/geom/LinearRing.js'; +import Polygon from 'ol/geom/Polygon.js'; +import MultiPoint from 'ol/geom/MultiPoint.js'; +import MultiLineString from 'ol/geom/MultiLineString.js'; +import MultiPolygon from 'ol/geom/MultiPolygon.js'; +import GeometryCollection from 'ol/geom/GeometryCollection.js'; import olLayerImage from 'ol/layer/Image.js'; import olLayerTile from 'ol/layer/Tile.js'; import olInteractionModify from 'ol/interaction/Modify.js'; @@ -33,6 +41,7 @@ import {CollectionEvent} from 'ol/Collection.js'; // @ts-ignore: not supported import import {OL3Parser} from 'jsts/io'; +import 'jsts/monkey.js'; /** @@ -323,7 +332,11 @@ function Controller($scope, $timeout, gettextCatalog, * @type {jsts.io.OL3Parser} * @private */ - this.jstsOL3Parser_ = new OL3Parser(); + this.jstsOL3Parser_ = new OL3Parser(undefined, { + geom: { + Point, LineString, LinearRing, Polygon, MultiPoint, MultiLineString, MultiPolygon, GeometryCollection + } + }); /** * The state of the feature determines whether the next 'save' request diff --git a/contribs/gmf/src/permalink/Permalink.js b/contribs/gmf/src/permalink/Permalink.js index d160d4fffe43..28d7da38e6e6 100644 --- a/contribs/gmf/src/permalink/Permalink.js +++ b/contribs/gmf/src/permalink/Permalink.js @@ -246,6 +246,10 @@ const ParamPrefix = { * gmfThemeManager, defaultTheme, gmfTreeManager, ngeoWfsPermalink, * ngeoAutoProjection and ngeoFeatures. * + * Used functionnalities: + * + * * default_theme: Theme to use by default. + * * @constructor * @param {angular.IQService} $q The Angular $q service. * @param {angular.ITimeoutService} $timeout Angular timeout service. @@ -260,7 +264,6 @@ const ParamPrefix = { * @ngInject * @ngdoc service * @ngname gmfPermalink - * @hidden */ export function PermalinkService( $q, $timeout, $rootScope, $injector, ngeoDebounce, gettextCatalog, ngeoEventHelper, ngeoStateManager, diff --git a/contribs/gmf/src/print/component.js b/contribs/gmf/src/print/component.js index 7ed2677d1ee0..5a377210a5cd 100644 --- a/contribs/gmf/src/print/component.js +++ b/contribs/gmf/src/print/component.js @@ -178,6 +178,12 @@ function gmfPrintTemplateUrl($element, $attrs, gmfPrintTemplateUrl) { * Note: The 'print' and 'cancel' functions can also be called via globals * events 'gmfStartPrint' and 'gmfCancelPrint'. * + * Used metadata: + * + * * hiDPILegendImages: The URLs to the hi DPI images used as a legend in the layer tree. For WMS and + * WMTS layers. + * * printNativeAngle: Whether the print should rotate the symbols. For layer groups (only). + * * @htmlAttribute {import("ol/Map.js").default} gmf-print-map The map. * @htmlAttribute {boolean} gmf-print-active A boolean that informs if the * panel is open or not. @@ -252,7 +258,6 @@ export class PrintController { * @param {angular.IFilterService} $filter Angular $filter service. * @param {PrintState} gmfPrintState GMF print state. * @param {import("gmf/theme/Themes.js").ThemesService} gmfThemes The gmf Themes service. - * @private * @ngInject * @ngdoc controller * @ngname GmfPrintController diff --git a/contribs/gmf/src/query/windowComponent.js b/contribs/gmf/src/query/windowComponent.js index 9609fd682287..e75b73c40940 100644 --- a/contribs/gmf/src/query/windowComponent.js +++ b/contribs/gmf/src/query/windowComponent.js @@ -557,7 +557,6 @@ QueryWindowController.prototype.highlightCurrentFeature_ = function(opt_lastFeat QueryWindowController.prototype.close = function() { this.open = false; this.clear(); - this.ngeoMapQuerent_.clear(); }; diff --git a/contribs/gmf/src/themes.js b/contribs/gmf/src/themes.js index 177cc877d326..9b2d5105e811 100644 --- a/contribs/gmf/src/themes.js +++ b/contribs/gmf/src/themes.js @@ -185,8 +185,6 @@ * values (for filters purpose). For WMS layers. * @property {boolean} [exclusiveGroup=false] Whether the group contain children that have to be mutually * exclusive, meaning that only one child may be ON at any time. - * @property {boolean} [geometry_validation=false] Whether geometries must be validated by PostgreSQL on - * edition. For WMS layers. * @property {string} [iconUrl] The URL of the icon to display in the layer tree. For WMS and WMTS layers. * @property {string} identifierAttributeField The field used in the 'display query window' as feature title. * For WMS layers. @@ -197,10 +195,6 @@ * (only). * @property {boolean|undefined} [isLegendExpanded=false] Whether the legend is expanded by default. For WMS * and WMTS layers. - * @property {string} [lastUpdateDateColumn] 'Date' column that will be automatically updated after editing - * an element. For WMS layers. - * @property {string} [lastUpdateUserColumn] 'User' column that will be automatically updated after editing - * an element. For WMS layers. * @property {boolean} [legend=false] Display the legend of this layers. For WMS and WMTS layers. * @property {string} [legendImage] The URL to the image used as a legend in the layer tree. For WMS and * WMTS layers. diff --git a/src/layertree/component.js b/src/layertree/component.js index 9916b74db640..ed7afa4ffad4 100644 --- a/src/layertree/component.js +++ b/src/layertree/component.js @@ -124,7 +124,7 @@ module.run( * @ngdoc directive * @ngname ngeoLayertree */ -function layertreeComponent(ngeoLayertreeTemplateUrl) { +function gmfLayertreeComponent(ngeoLayertreeTemplateUrl) { return { restrict: 'A', scope: true, @@ -134,7 +134,7 @@ function layertreeComponent(ngeoLayertreeTemplateUrl) { } -module.directive('ngeoLayertree', layertreeComponent); +module.directive('ngeoLayertree', gmfLayertreeComponent); export default module;