-
${_i18n.widgets.ShareDialog.extent}
+
+
+ ${_i18n.widgets.ShareDialog.extent}
-
-
-
+
+
-
+
+
-
${_i18n.widgets.ShareDialog.size}
-
+ ${_i18n.widgets.ShareDialog.size}
+
diff --git a/js/dijit/templates/instructions.french.html b/js/dijit/templates/instructions.french.html
new file mode 100644
index 00000000..a8722bf5
--- /dev/null
+++ b/js/dijit/templates/instructions.french.html
@@ -0,0 +1,12 @@
+
+
Outre la souris, vous pouvez utiliser les raccourcis suivants:
+
+ La touche Tab pour naviguer d’un élément à l’autre.
+ MAJ Tab pour naviguer vers l’arrière.
+ La barre d’ESPACEMENT pour activer une sélection plus précise.
+ La touche ENTRÉE pour activer l’élément choisi.
+ Appuyer sur Alt + flèche vers le bas pour ouvrir une liste déroulante.
+ La touche Alt avec un numéro pour naviguer rapidement (l’indice s’affiche).
+ La touche ÉCHAPPEMENT pour aller au point de départ de l’élément choisi.
+
+
\ No newline at end of file
diff --git a/js/dijit/templates/instructions.html b/js/dijit/templates/instructions.html
new file mode 100644
index 00000000..6b90d019
--- /dev/null
+++ b/js/dijit/templates/instructions.html
@@ -0,0 +1,12 @@
+
+
In addition to the mouse you may:
+
+ Use Tab key to navigate from item to item.
+ Use SHIFT Tab to navigate backwards.
+ Hit SPACE bar to toggle a focused check box.
+ Press ENTER to activate the focused item.
+ Press Alt + Arrow-Down to expand a combo box.
+ Use Alt with a number to fast navigate (hint will display.)
+ Use ESCAPE to go to the parent of the focus element.
+
+
\ No newline at end of file
diff --git a/js/has-config.js b/js/has-config.js
index f4390842..6547176b 100644
--- a/js/has-config.js
+++ b/js/has-config.js
@@ -4,6 +4,7 @@ https://dojotoolkit.org/documentation/tutorials/1.8/device_optimized_builds/
http://dante.dojotoolkit.org/hasjs/tests/runTests.html*/
define(["dojo/has"], function (has) {
+
var getTool = function (name, config) {
var tool = false;
for (var i = 0; i < config.tools.length; i++) {
@@ -16,6 +17,14 @@ define(["dojo/has"], function (has) {
};
/*App capabilities*/
+ has.add("navigation", function (g) {
+ var navigation = getTool("navigation", g.config);
+ //overwrite the default with app settings
+ if (g.config.hasOwnProperty("navigation")) {
+ navigation = g.config.navigation;
+ }
+ return navigation;
+ });
has.add("search", function (g) {
var search = g.config.search || false;
//overwrite the default with app settings
@@ -87,57 +96,37 @@ define(["dojo/has"], function (has) {
}
return home;
});
- has.add("layers", function (g) {
- var layers = getTool("layers", g.config);
+ has.add("features", function (g) {
+ var features = getTool("features", g.config);
//overwrite the default with app settings
- if (g.config.hasOwnProperty("tool_layers")) {
- layers = g.config.tool_layers;
+ if (g.config.hasOwnProperty("tool_features")) {
+ features = g.config.tool_features;
}
- return layers;
+ return features;
});
-
- has.add("layers-sublayers", function (g) {
- var subLayers = false;
- for (var i = 0; i < g.config.tools.length; i++) {
- if (g.config.tools[i].name === "layers") {
- subLayers = g.config.tools[i].sublayers;
- break;
- }
- }
+ has.add("filter", function (g) {
+ var filter = getTool("filter", g.config);
//overwrite the default with app settings
- if (g.config.hasOwnProperty("tool_sublayers")) {
- subLayers = g.config.tool_sublayers;
+ if (g.config.hasOwnProperty("tool_filter")) {
+ filter = g.config.tool_filter;
}
- return subLayers;
+ return filter;
});
- has.add("layers-legend", function (g) {
- var layerLegend = false;
- for (var i = 0; i < g.config.tools.length; i++) {
- if (g.config.tools[i].name === "layers") {
- layerLegend = g.config.tools[i].legend;
- break;
- }
- }
+ has.add("layers", function (g) {
+ var layers = getTool("layers", g.config);
//overwrite the default with app settings
- if (g.config.hasOwnProperty("tool_layerlegend")) {
- layerLegend = g.config.tool_layerlegend;
+ if (g.config.hasOwnProperty("tool_layers")) {
+ layers = g.config.tool_layers;
}
- return layerLegend;
+ return layers;
});
-
- has.add("layers-opacity", function (g) {
- var opacity = false;
- for (var i = 0; i < g.config.tools.length; i++) {
- if (g.config.tools[i].name === "layers") {
- opacity = g.config.tools[i].opacityslider;
- break;
- }
- }
+ has.add("instructions", function (g) {
+ var instructions = getTool("instructions", g.config);
//overwrite the default with app settings
- if (g.config.hasOwnProperty("tool_opacity")) {
- opacity = g.config.tool_opacity;
+ if (g.config.hasOwnProperty("tool_instructions")) {
+ instructions = g.config.tool_instructions;
}
- return opacity;
+ return instructions;
});
has.add("legend", function (g) {
@@ -224,6 +213,8 @@ define(["dojo/has"], function (has) {
return printLayouts;
});
+
+
has.add("share", function (g) {
var share = getTool("share", g.config);
//overwrite the default with app settings
diff --git a/js/main.js b/js/main.js
index 5811a910..e3692c35 100755
--- a/js/main.js
+++ b/js/main.js
@@ -13,144 +13,136 @@
| See the License for the specific language governing permissions and
| limitations under the License.
*/
-define([
- "dojo/ready",
- "dojo/json",
- "dojo/i18n!esri/nls/jsapi",
+define(["dojo/ready",
+ "dojo/aspect", "dijit/registry",
+ "dojo/json", "dojo/_base/array", "dojo/_base/Color", "dojo/_base/declare",
+ "dojo/_base/lang", "dojo/dom", "dojo/dom-geometry", "dojo/dom-attr", "dojo/dom-class",
+ "dojo/dom-construct", "dojo/dom-style", "dojo/on", "dojo/Deferred", "dojo/promise/all",
+ "dojo/query", "dijit/Menu", "dijit/CheckedMenuItem", "application/toolbar",
+ "application/has-config", "esri/arcgis/utils", "esri/lang",
+ "dijit/layout/BorderContainer", "dijit/layout/ContentPane", "dijit/focus",
+ "esri/tasks/query",
+ "esri/dijit/HomeButton", "esri/dijit/LocateButton",
+ "esri/dijit/Legend", "esri/dijit/BasemapGallery",
+ "dojo/i18n!application/nls/resources",
+ "dojo/i18n!application/nls/BaseMapLabels",
+ "esri/dijit/Measurement", "esri/dijit/OverviewMap", "esri/geometry/Extent",
+ "esri/layers/FeatureLayer", "application/NavToolBar/NavToolBar",
+ "application/FeatureList/FeatureList", "application/Filters/Filters", "application/TableOfContents",
+ "application/LanguageSelect/LanguageSelect",
+ "application/ShareDialog", //"application/SearchSources",
+ "esri/symbols/SimpleMarkerSymbol", "esri/symbols/PictureMarkerSymbol", "esri/graphic",
+ "esri/dijit/InfoWindow",
+ "dojo/NodeList-dom", "dojo/NodeList-traverse"],
+ function (
+ ready,
+ aspect, registry,
+ JSON, array, Color, declare,
+ lang, dom, domGeometry, domAttr, domClass,
+ domConstruct, domStyle, on, Deferred, all,
+ query, Menu, CheckedMenuItem, Toolbar,
+ has, arcgisUtils, esriLang,
+ BorderContainer, ContentPane, focusUtil,
+ Query,
+ HomeButton, LocateButton,
+ Legend, BasemapGallery,
+ i18n, i18n_BaseMapLabels,
+ Measurement, OverviewMap, Extent,
+ FeatureLayer, NavToolBar,
+ FeatureList, Filters, TableOfContents, LanguageSelect,
+ ShareDialog, //SearchSources,
+ SimpleMarkerSymbol, PictureMarkerSymbol, Graphic,
+ InfoWindow) {
- "dojo/_base/array",
- "dojo/_base/Color",
- "dojo/_base/declare",
- "dojo/_base/lang",
-
- "dojo/dom",
- "dojo/dom-geometry",
- "dojo/dom-attr",
- "dojo/dom-class",
- "dojo/dom-construct",
- "dojo/dom-style",
-
- "dojo/on",
- "dojo/Deferred",
- "dojo/promise/all",
- "dojo/query",
-
- "dijit/registry",
- "dijit/Menu",
- "dijit/CheckedMenuItem",
-
- "application/toolbar",
- "application/has-config",
- "application/ShareDialog",
- "application/SearchSources",
-
- "esri/arcgis/utils",
- "esri/lang",
- "esri/urlUtils",
-
- "esri/dijit/HomeButton",
- "esri/dijit/LocateButton",
- "esri/dijit/Legend",
- "esri/dijit/BasemapGallery",
- "esri/dijit/Measurement",
- "esri/dijit/OverviewMap",
- "esri/dijit/LayerList",
-
- "esri/geometry/Extent",
- "esri/layers/FeatureLayer"
- ], function (
- ready,JSON,
-
- esriBundle,
-
- array, Color, declare, lang,
-
- dom, domGeometry, domAttr, domClass,
- domConstruct, domStyle,
-
- on, Deferred, all, query,
-
- registry, Menu, CheckedMenuItem,
-
- Toolbar, has,
- ShareDialog, SearchSources,
-
- arcgisUtils, esriLang, urlUtils,
-
- HomeButton, LocateButton, Legend,
- BasemapGallery, Measurement,
- OverviewMap, LayerList,
-
- Extent, FeatureLayer
-
- ) {
return declare(null, {
config: {},
color: null,
theme: null,
map: null,
+ initExt: null,
mapExt: null,
editorDiv: null,
editor: null,
editableLayers: null,
timeFormats: ["shortDateShortTime", "shortDateLEShortTime", "shortDateShortTime24", "shortDateLEShortTime24", "shortDateLongTime", "shortDateLELongTime", "shortDateLongTime24", "shortDateLELongTime24"],
+
startup: function (config) {
// config will contain application and user defined info for the template such as i18n strings, the web map id
// and application id and any url parameters and any application specific configuration information.
if (config) {
this.config = config;
- this.color = this._setColor(this.config.color);
- this.theme = this._setColor(this.config.theme);
-
- // Create and add custom style sheet
- if(this.config.customstyle){
- var style = document.createElement("style");
- style.appendChild(document.createTextNode(this.config.customstyle));
- document.head.appendChild(style);
- }
-
-
+ this.color = this.setColor(this.config.color);
+ this.hoverColor = typeof(this.config.hoverColor)=='undefined' ? this.setColor('#000000', 0.4) : this.setColor(this.config.hoverColor, 0.9);
+ this.focusColor = typeof(this.config.focusColor)=='undefined' ? this.setColor('#1f1f1f', 0.4) : this.setColor(this.config.focusColor, 0.9);
+ this.activeColor = typeof(this.config.activeColor)=='undefined' ? this.focusColor : this.setColor(this.config.activeColor, 0.9);
+ this.theme = this.setColor(this.config.theme);
// document ready
ready(lang.hitch(this, function () {
//supply either the webmap id or, if available, the item info
var itemInfo = this.config.itemInfo || this.config.webmap;
-
- // Setup the modal overlay if enabled
- if(this.config.splashModal){
- domClass.remove("modal", "hide-modal");
- var title = this.config.splashTitle || "";
- var content = this.config.splashContent || "";
- dom.byId("modalTitle").innerHTML = title;
- dom.byId("modalContent").innerHTML = content;
- // Close button handler for the overlay
- on(dom.byId("closeOverlay"), "click", lang.hitch(this, function(){
- this._createWebMap(itemInfo);
- domClass.add("modal", "hide-modal");
- }));
- }else{
- this._createWebMap(itemInfo);
+ //If a custom extent is set as a url parameter handle that before creating the map
+ if (this.config.extent) {
+ var extArray = decodeURIComponent(this.config.extent).split(",");
+
+ if (extArray.length === 4) {
+ itemInfo.item.extent = [
+ [parseFloat(extArray[0]), parseFloat(extArray[1])],
+ [parseFloat(extArray[2]), parseFloat(extArray[3])]
+ ];
+ } else if (extArray.length === 5) {
+ this.initExt = new Extent(JSON.parse(this.config.extent));
+ }
}
-
-
-
+ this._createWebMap(itemInfo);
}));
} else {
var error = new Error("Main:: Config is not defined");
this.reportError(error);
}
+
+ var languages = [
+ {
+ code:this.config.lang1code,
+ img:this.config.lang1imageSrc,
+ shortName:this.config.lang1shortName,
+ name:this.config.lang1name,
+ appId:this.config.lang1appId
+ },
+ {
+ code:this.config.lang2code,
+ img:this.config.lang2imageSrc,
+ shortName:this.config.lang2shortName,
+ name:this.config.lang2name,
+ appId:this.config.lang2appId
+ },
+ {
+ code:this.config.lang3code,
+ img:this.config.lang3imageSrc,
+ shortName:this.config.lang3shortName,
+ name:this.config.lang3name,
+ appId:this.config.lang3appId
+ }
+ ];
+ new LanguageSelect({
+ locale: document.documentElement.lang,
+ //location: window.location,
+ languages:languages,
+ textColor:this.titleColor,
+ showLabel:this.config.languageLabel
+ }, dojo.byId('languageSelectNode')).startup();
},
reportError: function (error) {
// remove loading class from body
- domClass.remove(document.body, "app-loading");
- domClass.add(document.body, "app-error");
+ domClass.replace(document.body, "app-error","app-loading");
// an error occurred - notify the user. In this example we pull the string from the
// resource.js file located in the nls folder because we've set the application up
// for localization. If you don't need to support multiple languages you can hardcode the
// strings here and comment out the call in index.html to get the localization strings.
// set message
var node = dom.byId("loading_message");
+
if (node) {
if (this.config && this.config.i18n) {
node.innerHTML = this.config.i18n.map.error + ": " + error.message;
@@ -159,20 +151,146 @@ define([
}
}
},
- // Map is ready
+
+ setColor: function (color, tr) {
+ var rgb = Color.fromHex(color).toRgb();
+ var outputColor = null;
+ if (has("ie") < 9) {
+ outputColor = color;
+ } else {
+ //rgba supported so add
+ rgb.push(tr);
+ outputColor = Color.fromArray(rgb);
+ }
+ return outputColor;
+ },
+
_mapLoaded: function () {
+ // this.map.resize();
+ // this.map.reposition();
+
query(".esriSimpleSlider").style("backgroundColor", this.theme.toString());
// remove loading class from body
+
domClass.remove(document.body, "app-loading");
- if(!this.config.popupPanel){
- //on(this.map.infoWindow, "selection-change", lang.hitch(this, this._movePopup));
- on(window, "orientationchange", lang.hitch(this, this._adjustPopupSize));
- this._adjustPopupSize();
+ on(window, "orientationchange", lang.hitch(this, this._adjustPopupSize));
+ this._adjustPopupSize();
+
+ var _map = this.map;
+
+ on(this.map.infoWindow, "show", lang.hitch(this, function() {
+ this._initPopup(this.map.infoWindow.domNode);
+ }));
+
+ on(this.map.infoWindow, "selection-change", lang.hitch(this, function() {
+ this._initPopup(this.map.infoWindow.domNode);
+ }));
+ },
+
+ _initPopup : function (node) {
+ images = node.querySelectorAll('img');
+ for (var i = 0; i
= 1) {
+ upper[0].focus();
+ } else {
+ skipToMap();
+ }
+ break;
+ case '0' :
+ if (event.altKey) {
+ skipSkip();
+ }
+ break;
+ default:
+ break;
+ }
+
+ });
+
+ on(document.body, 'keyup', function(event) {
+ if(!event.altKey) {
+ query('.goThereHint').forEach(function(h) {
+ domStyle.set(h, 'display','');
+ });
+ }
+ });
+
+ if(this.config.alt_keys) {
+ domConstruct.create("div", {
+ class:'goThereHint',
+ innerHTML: 'Alt + 1 '+this.config.i18n.skip.tools,
+ style:'left:20%; top:10px;'
+ }, dom.byId('panelTools'));
+
+ domConstruct.create("div", {
+ class:'goThereHint',
+ innerHTML: 'Alt + 2 '+this.config.i18n.skip.search,
+ style:'left:20%; top:50%;'
+ }, dom.byId('panelSearch'));
+
+ domConstruct.create("div", {
+ class:'goThereHint',
+ innerHTML: 'Alt + 3 '+this.config.i18n.skip.content,
+ style:'left:20%; top:50%;'
+ }, dom.byId('panelPages'));
+
+ domConstruct.create("div", {
+ class:'goThereHint',
+ innerHTML: 'Alt + 4 '+this.config.i18n.skip.splitter,
+ style:'left:-30px; top:40%;'
+ }, dom.byId('dijit_layout_ContentPane_1_splitter'));
+
+ domConstruct.create("div", {
+ class:'goThereHint',
+ innerHTML: 'Alt + 5 '+this.config.i18n.skip.map,
+ style:'left:10%; top:30%'
+ }, dom.byId('mapDiv'));
+
+ domConstruct.create("div", {
+ class:'goThereHint',
+ innerHTML: 'Alt + 6 '+this.config.i18n.skip.help,
+ style:'left:20%; top:-75%;'
+ }, dom.byId('panelBottom'));
+ }
+
+ var skipTools = query('.skip #skip-tools')[0];
+ var skipSearch = query('.skip #skip-search')[0];
+ var skipContent = query('.skip #skip-content')[0];
+ var skipSplitter = query('.skip #skip-splitter')[0];
+ var skipMap = query('.skip #skip-map')[0];
+ var skipInstructions = query('.skip #skip-instructions')[0];
+ var skipFeature = query('.skip #skip-feature')[0];
+
+ dojo.html.set(skipTools, "1. "+this.config.i18n.skip.tools);
+ dojo.html.set(skipSearch, "2. "+this.config.i18n.skip.search);
+ dojo.html.set(skipContent, "3. "+this.config.i18n.skip.content);
+ dojo.html.set(skipSplitter, "4. "+this.config.i18n.skip.splitter);
+ dojo.html.set(skipMap, "5. "+this.config.i18n.skip.map);
+ dojo.html.set(skipInstructions, "6. "+this.config.i18n.skip.help);
+ dojo.html.set(skipFeature, "7. "+this.config.i18n.skip.featureDetaills);
+
+ skipTools.addEventListener('click', function (e) { skipToTools(); });
+ skipSearch.addEventListener('click', function (e) { skipToSearch(); });
+ skipContent.addEventListener('click', function (e) { skipToContent(); });
+ skipSplitter.addEventListener('click', function (e) { skipToSplitter(); });
+ skipMap.addEventListener('click', function (e) { skipToMap(); });
+ skipInstructions.addEventListener('click', function (e) { skipToInstructions(); });
+ skipFeature.addEventListener('click', function (e) { skipToFeature(); });
+
+ query('.skip').forEach(function(h) {
+ h.addEventListener('keydown', function (e) {
+ if(e.key === "Enter" || e.key === " " || e.char === " ")
+ {
+ e.target.click();
+ e.preventDefault();
+ }
+ });
+ });
+
+ query('.skip a').forEach(function(a) {
+ a.onfocus = lang.hitch(a, function () {
+ console.log(this);
+ domAttr.set(this, "aria-hidden", "false");
+ console.log(this);
+ });
+ a.onblur = lang.hitch(a, function () {
+ console.log(this);
+ domAttr.set(this, "aria-hidden", "true");
+ console.log(this);
+ });
+ });
+
+ dojo.html.set(dom.byId('panelBottomSpan'), this.config.i18n.pressAlt);
+ dojo.html.set(dom.byId('searchLabel'), this.config.i18n.search);
+
+ skipSkip = function() {
+ dom.byId('skip-tools').focus();
+ };
+
+ skipToTools = function() {
+ query('#panelTools .panelToolActive input[type="image"]')[0].focus();
+ //dom.byId('panelTools').focus();
+ };
+
+ skipToSearch = function() {
+ dom.byId('search_input').focus();
+ };
+
+ skipToContent = function() {
+ //dom.byId('panelPages').focus();
+ dojo.query(".page.showAttr .pageBody")[0].focus();
+ };
+
+ skipToSplitter = function() {
+ dom.byId('dijit_layout_ContentPane_1_splitter').focus();
+ };
+
+ skipToMap = function() {
+ //document.querySelector('.esriSimpleSliderIncrementButton input').focus();
+ document.querySelector('#mapDiv').focus();
+ };
+
+ skipToInstructions = function() {
+ var activeTool = query('.panelToolActive');
+ if(activeTool && activeTool.length>0) {
+ activeTool = activeTool[0].childNodes[0];
+ activeTool.click();
+ }
+ dom.byId('instructionsDiv').focus();
+ };
+
+ skipToFeature = function() {
+ if(featureList) {
+ featureList.FocusDetails();
+ }
+ };
+ },
+
+ featureList : null,
+
+ _addFeatures: function (tool, toolbar) {
+ //Add the legend tool to the toolbar. Only activated if the web map has operational layers.
+ var deferred = new Deferred();
+ if (has("features")) {
+ var featuresDiv = toolbar.createTool(tool, "", "reload1.gif", "featureSelected");
+
+ var layers = this.config.response.itemInfo.itemData.operationalLayers;
+
+ featureList = new FeatureList({
+ map: this.map,
+ layers: layers,
+ toolbar: toolbar,
+ animatedMarker: this.config.animated_marker,
+ markerImage: this.config.marker,
+ markerSize: this.config.marker_size
+ }, featuresDiv);
+ featureList.startup();
+
+ // on(toolbar, 'updateTool_features', lang.hitch(this, function(name) {
+ // dom.byId('pageBody_features').focus();
+ // }));
+
+ deferred.resolve(true);
+ }
+ else {
+ // window._prevSelected = null;
+ deferred.resolve(false);
+ }
+
+ return deferred.promise;
+ },
+
+ navDeferred : null,
+
+ _addNavigation: function (tool, oldNaviagationToolBar, deferred) {
+ var navToolBar = domConstruct.create("div", {
+ id: "newNaviagationToolBar",
+ });
+
+ nav = new NavToolBar({
+ map: this.map,
+ navToolBar: oldNaviagationToolBar,
+ iconColor: this.config.icons,
+ newIcons: this.config.new_icons?'.new':'',
+ zoomColor: this.focusColor,
+ }, navToolBar);
+ nav.startup();
+ deferred.resolve(true);
+ return deferred.promise;
+ },
+
+ _addFilter: function (tool, toolbar) {
+ //Add the legend tool to the toolbar. Only activated if the web map has operational layers.
+ var deferred = new Deferred();
+ if (has("filter")) {
+ var filterDiv = toolbar.createTool(tool, "", "", "somefilters");
+
+ var layers = this.config.response.itemInfo.itemData.operationalLayers;
+
+ filter = new Filters({
+ map: this.map,
+ layers: layers,
+ toolbar: toolbar,
+ }, filterDiv);
+ filter.startup();
+
+ // on(toolbar, 'updateTool_filter', lang.hitch(this, function(name) {
+ // dom.byId('pageBody_filter').focus();
+ // }));
+
+ deferred.resolve(true);
+ }
+ else {
+ // window._prevSelected = null;
+ deferred.resolve(false);
+ }
+
+ return deferred.promise;
},
- _addBasemapGallery: function (tool, toolbar, panelClass) {
- //Add the basemap gallery to the toolbar.
+
+ _addBasemapGallery: function (tool, toolbar) {
var deferred = new Deferred();
if (has("basemap")) {
- var basemapDiv = toolbar.createTool(tool, panelClass);
+ var basemapDiv = toolbar.createTool(tool);
var basemap = new BasemapGallery({
id: "basemapGallery",
map: this.map,
@@ -312,7 +661,85 @@ define([
portalUrl: this.config.sharinghost,
basemapsGroup: this._getBasemapGroup()
}, domConstruct.create("div", {}, basemapDiv));
+
basemap.startup();
+
+ on(basemap, "load", lang.hitch(basemap, function () {
+ var list = this.domNode.querySelector("div");
+ domAttr.set(list, "role", "list");
+
+ var galleryNodeObserver = new MutationObserver(function(mutations) {
+ mutations.forEach(function(mutation) {
+ //console.log(mutation);
+ var node = mutation.target;
+ var aSpan = node.querySelector("a span");
+ var l = aSpan.innerText;
+ if(dojo.hasClass(node, "esriBasemapGallerySelectedNode"))
+ {
+ l += ' '+this.config.i18n.tools.basemapGallery.selected;
+ }
+ l += '.';
+ //node.querySelector('a').focus();
+ domAttr.set(aSpan, 'aria-label', l);
+ //aSpan.focus();
+ });
+ });
+
+ var observerCfg = { attributes: true, childList: false, characterData: false };
+
+ var nodes = this.domNode.querySelectorAll(".esriBasemapGalleryNode");
+ array.forEach(nodes, function(node){
+ domAttr.set(node, "role", "listitem");
+ //domAttr.set(node, "aria-hidden", "true");
+
+ galleryNodeObserver.observe(node, observerCfg);
+
+ var img = node.querySelector("img");
+ img.alt='';
+ domAttr.set(img, "aria-hidden", true);
+ domAttr.remove(img, "title");
+ domAttr.remove(img, "tabindex");
+
+ var aNode = node.querySelector("a");
+ domAttr.set(aNode, "tabindex", -1);
+ var labelNode = node.querySelector(".esriBasemapGalleryLabelContainer");
+ domAttr.remove(labelNode.firstChild, "alt");
+ domAttr.remove(labelNode.firstChild, "title");
+ dojo.place(labelNode, aNode, "last");
+
+ var aSpan = node.querySelector("a span");
+ var aSpanLabel = aSpan.innerHTML.toLowerCase().replace(/\s/g, '_');
+ try {
+ var localizedLabel = i18n_BaseMapLabels.baseMapLabels[aSpanLabel];
+ if(localizedLabel && localizedLabel !== undefined)
+ aSpan.innerText = localizedLabel;
+ var l = aSpan.innerText;
+ if(dojo.hasClass(node, "esriBasemapGallerySelectedNode"))
+ {
+ l += ' '+this.config.i18n.tools.basemapGallery.selected;
+ }
+ l += '.';
+ domAttr.set(aSpan, 'aria-label', l);
+ //img.alt=aSpan.innerText;
+ } catch(e) {}
+
+ domAttr.set(labelNode, "tabindex", 0);
+ on(img, "click", function() { node.focus();});
+ on(node,"keydown", function(ev) {
+ if(ev.key === "Enter" || ev.key === " " || ev.char === " ") {
+ aNode.click();
+ } else if(ev.key === "Tab" && !ev.shiftKey) {
+ if(node.nextElementSibling.nodeName != "BR") {
+ node.nextElementSibling.focus();
+ } else {
+ document.querySelector('#dijit_layout_ContentPane_0_splitter').focus();
+ }
+ } else if(ev.key === "Tab" && ev.shiftKey) {
+ node.focus();
+ }
+ });
+ });
+ }));
deferred.resolve(true);
} else {
deferred.resolve(false);
@@ -321,67 +748,139 @@ define([
return deferred.promise;
},
- _addBookmarks: function (tool, toolbar, panelClass) {
- //Add the bookmarks tool to the toolbar. Only activated if the webmap contains bookmarks.
+ _addBookmarks: function (tool, toolbar) {
var deferred = new Deferred();
if (this.config.response.itemInfo.itemData.bookmarks) {
- //Conditionally load this module since most apps won't have bookmarks
+
require(["application/has-config!bookmarks?esri/dijit/Bookmarks"], lang.hitch(this, function (Bookmarks) {
if (!Bookmarks) {
deferred.resolve(false);
return;
}
- var bookmarkDiv = toolbar.createTool(tool, panelClass);
+ var bookmarkDiv = toolbar.createTool(tool);
+ // var bookmarkDiv = domConstruct.create("div",{ class: "margin"}, bDiv);
var bookmarks = new Bookmarks({
map: this.map,
bookmarks: this.config.response.itemInfo.itemData.bookmarks
}, domConstruct.create("div", {}, bookmarkDiv));
+ items = bookmarks.bookmarkDomNode.querySelectorAll('.esriBookmarkItem');
+ if(items && items.length>0)
+ {
+ itemsTable = items[0].parentNode.parentNode.parentNode.parentNode;
+ var header = document.createElement("tr");
+ header.innerHTML = "Bookmarks ";
+ itemsTable.insertBefore(header, items[0].parentNode.parentNode.parentNode);
+ domAttr.set(itemsTable,"role","list");
+
+ for(i=0; i";
+ var detailDiv = toolbar.createTool(tool);
+ domConstruct.create('div',{
+ tabindex:0
+ });
+ detailDiv.innerHTML = ""+description+"
";
+ detailDiv = dojo.query("#detailDiv")[0];
+ if(!has("instructions"))
+ domClass.add(detailDiv, "detailFull");
+ else
+ domClass.add(detailDiv, "detailHalf");
+
+ var detailBtn = dojo.query("#toolButton_details")[0];
+ domClass.add(detailBtn, "panelToolDefault");
}
deferred.resolve(true);
} else {
- deferred.resolve(false);
+ deferred.resolve(true);
}
return deferred.promise;
+ },
+
+ _addInstructions: function (tool, toolbar, deferedDetails) {
+ var deferred = new Deferred();
+ if (!has("instructions")) {
+ deferred.resolve(false);
+ }
+ else
+ {
+ if(!has("details"))
+ {
+ require(["dojo/text!application/dijit/templates/"+this.config.i18n.instructions+".html"],
+ function(instructionsText){
+ var instructionsDiv = toolbar.createTool(tool);
+ domConstruct.create('div',{
+ id:"instructionsDiv",
+ innerHTML: instructionsText,
+ tabindex: 0
+ }, domConstruct.create("div", {}, instructionsDiv));
+ });
+
+ var instructionsBtn = dojo.query("#toolButton_instructions")[0];
+ domClass.add(instructionsBtn, "panelToolDefault");
+ }
+ else {
+ deferedDetails.then(lang.hitch(this, function(r) {
+ require(["dojo/text!application/dijit/templates/"+this.config.i18n.instructions+".html"],
+ function(instructionsText){
+ var instructionsDiv = domConstruct.create('div',{
+ id:"instructionsDiv",
+ innerHTML: instructionsText,
+ tabindex: 0
+ }, dom.byId("pageBody_details"));
+ });
+
+ on(toolbar, 'updateTool_details', this._adjustDetails);
+ on(this.map, 'resize', this._adjustDetails);
+ document.body.onresize = this._adjustDetails;
+ }));
+ }
+ deferred.resolve(true);
+ }
+ return deferred.promise;
+ },
+ _adjustDetails :function() {
+ try {
+ var pageBody = dojo.byId('pageBody_details');
+ var detailDiv = dojo.byId('detailDiv');
+ detailDiv.style.maxHeight=(pageBody.clientHeight-instructionsDiv.clientHeight - 30) + 'px';
+ } catch (e) {
+ /* ignore instructionDiv not defined error: will come defined next time! */
+ }
},
- _addEditor: function (tool, toolbar, panelClass) {
+ _addEditor: function (tool, toolbar) {
//Add the editor widget to the toolbar if the web map contains editable layers
var deferred = new Deferred();
this.editableLayers = this._getEditableLayers(this.config.response.itemInfo.itemData.operationalLayers);
if (has("edit") && this.editableLayers.length > 0) {
if (this.editableLayers.length > 0) {
- this.editorDiv = toolbar.createTool(tool, panelClass);
+ this.editorDiv = toolbar.createTool(tool);
return this._createEditor();
} else {
console.log("No Editable Layers");
@@ -393,6 +892,7 @@ define([
return deferred.promise;
},
+
_createEditor: function () {
var deferred = new Deferred();
//Dynamically load since many apps won't have editable layers
@@ -417,15 +917,17 @@ define([
time: true
};
}
- //Add all editable fields even if not visible.
- //if (field.visible) {
- fieldInfos.push(field);
- //}
+
+ if (field.visible) {
+ fieldInfos.push(field);
+ }
+
}));
layer.fieldInfos = fieldInfos;
}
}));
+
var settings = {
map: this.map,
layerInfos: this.editableLayers,
@@ -435,22 +937,37 @@ define([
settings: settings
}, domConstruct.create("div", {}, this.editorDiv));
-
this.editor.startup();
deferred.resolve(true);
-
}));
+
return deferred.promise;
+ },
+
+ _getEditableLayers: function (layers) {
+ var layerInfos = [];
+ array.forEach(layers, lang.hitch(this, function (layer) {
+ if (layer && layer.layerObject) {
+ var eLayer = layer.layerObject;
+ if (eLayer instanceof FeatureLayer && eLayer.isEditable()) {
+ layerInfos.push({
+ "featureLayer": eLayer
+ });
+ }
+ }
+ }));
+ return layerInfos;
},
+
_destroyEditor: function () {
if (this.editor) {
this.editor.destroy();
this.editor = null;
}
-
},
- _addLayers: function (tool, toolbar, panelClass) {
+
+ _addLayers: function (tool, toolbar) {
//Toggle layer visibility if web map has operational layers
var deferred = new Deferred();
@@ -460,27 +977,20 @@ define([
deferred.resolve(false);
} else {
if (has("layers")) {
+ panelClass = "";
- //Use small panel class if layer layer is less than 5
- if (layers.length < 5) {
- panelClass = "small";
- } else if (layers.length < 15) {
- panelClass = "medium";
- } else {
- panelClass = "large";
- }
- var layersDiv = toolbar.createTool(tool, panelClass);
+ var layersDivDesc = toolbar.createTool(tool);
+ // var layersDivDesc = domConstruct.create("div", {class:'margin'}, layersDiv);
- var toc = new LayerList({
+ var toc = new TableOfContents({
map: this.map,
- showSubLayers: has("layers-sublayers"),
- subLayers: has("layers-sublayers"),
- showLegend: has("layers-legend"),
- showOpacitySlider: has("layers-opacity"),
- layers: arcgisUtils.getLayerList(this.config.response)
- }, domConstruct.create("div", {}, layersDiv));
+ layers: layers
+ }, domConstruct.create("div", {}, layersDivDesc));
toc.startup();
+ // on(toolbar, 'updateTool_layers', lang.hitch(this, function(name) {
+ // dom.byId('pageBody_layers').focus();
+ // }));
deferred.resolve(true);
} else {
@@ -489,60 +999,119 @@ define([
}
return deferred.promise;
},
- _addLegend: function (tool, toolbar, panelClass) {
+
+ _addLegend: function (tool, toolbar) {
//Add the legend tool to the toolbar. Only activated if the web map has operational layers.
var deferred = new Deferred();
var layers = arcgisUtils.getLegendLayers(this.config.response);
-
if (layers.length === 0) {
deferred.resolve(false);
} else {
if (has("legend")) {
- var legendLength = 0;
- array.forEach(layers, lang.hitch(this, function (layer) {
- if (layer.infos && layer.infos.length) {
- legendLength += layer.infos.length;
- }
- }));
-
- if (legendLength.length < 5) {
- panelClass = "small";
- } else if (legendLength.length < 15) {
- panelClass = "medium";
- } else {
- panelClass = "large";
- }
-
- var legendDiv = toolbar.createTool(tool, panelClass);
+ var legendDiv = toolbar.createTool(tool, "");
var legend = new Legend({
map: this.map,
layerInfos: layers
- }, domConstruct.create("div", {}, legendDiv));
+ }, domConstruct.create("div", {role:'application'}, legendDiv));//Desc));
domClass.add(legend.domNode, "legend");
legend.startup();
- if (this.config.activeTool !== "") {
- toolbar.activateTool(this.config.activeTool || "legend");
- } else {
- toolbar.closePage();
- }
+
+ on(toolbar, 'updateTool_legend', lang.hitch(this, function(name) {
+ fixLegend();
+ // dom.byId('pageBody_legend').focus();
+ }));
+
+ var fixLegend = function() {
+ var tables = legend.domNode.querySelectorAll("table");
+ if(tables && tables.length>0)
+ {
+ for(var t=0; t0)
+ {
+ for(var s=0; s0)
+ {
+ for(var i=0; i -this.div.clientHeight/2) {
+ dojo.style(this.div, 'top', --top + 'px');
+ }
+ break;
+ case 40 : // down
+ if(top < this.div.parentElement.offsetHeight - this.div.clientHeight/2) {
+ dojo.style(this.div, 'top', ++top + 'px');
+ }
+ break;
+ case 37 : // left
+ if(left > -this.div.clientWidth/2) {
+ dojo.style(this.div, 'left', --left + 'px');
+ }
+ break;
+ case 39 : // right
+ if(left < this.div.parentElement.offsetWidth - this.div.clientWidth/2) {
+ dojo.style(this.div, 'left', ++left + 'px');
+ }
+ break;
+ }
+ switch (event.keyCode) {
+ case 9: // tab
+ case 33: // PgUp
+ case 34: // PgDn
+ case 27: // Esc
+ break;
+ default:
+ event.stopPropagation();
+ event.preventDefault();
+ break;
+ }
+ }));
+
+ on(onButton, 'keyup', lang.hitch(map, function(event) {
+ switch (event.keyCode) {
+ case 38 : // up
+ case 40 : // down
+ case 37 : // left
+ case 39 : // right
+ var a;
+ this._moveStopHandler(a);
+ break;
+ }
+ switch (event.keyCode) {
+ case 9: // tab
+ case 33: // PgUp
+ case 34: // PgDn
+ case 27: // Esc
+ break;
+ default:
+ event.stopPropagation();
+ event.preventDefault();
+ break;
+ }
+ }));
+ },
+
+ _addPrint: function (tool, toolbar) {
+ //Add the print widget to the toolbar. TODO: test custom layouts.
var deferred = new Deferred(),
- print = null;
- require(["application/has-config!print?application/PrintConfig", "application/has-config!print?esri/dijit/Print"], lang.hitch(this, function (PrintConfig, Print) {
- if (!PrintConfig || !Print) {
+ legendNode = null,
+ print = null;
+
+ require(["application/has-config!print?esri/dijit/Print"], lang.hitch(this, function (Print) {
+ if (!Print) {
deferred.resolve(false);
return;
}
- var printDiv = toolbar.createTool(tool, panelClass);
- var format = null;
- array.forEach(this.config.tools, function (tool) {
- if (tool.name === "print") {
- format = tool.format;
- }
- });
- if (this.config.hasOwnProperty("tool_print_format")) {
- format = this.config.tool_print_format;
- }
+
var layoutOptions = {
"titleText": this.config.title,
"scalebarUnit": this.config.units,
"legendLayers": []
};
- var printOptions = {
- legendLayers: this.config.response,
- layouts: has("print-layouts"),
- format: format.toLowerCase() || null,
- printTaskUrl: this.config.helperServices.printTask.url,
- printi18n: this.config.i18n.tools.print,
- layoutOptions: layoutOptions
- };
- if(this.config.helperServices.printTask && this.config.helperServices.printTask.templates){
- printOptions.templates = this.config.helperServices.printTask.templates;
+
+ var printDiv = domConstruct.create("div", {
+ class:"PrintDialog"
+ }, toolbar.createTool(tool));
+ //get format
+ this.format = "PDF"; //default if nothing is specified
+ for (var i = 0; i < this.config.tools.length; i++) {
+ if (this.config.tools[i].name === "print") {
+ var f = this.config.tools[i].format;
+ this.format = f.toLowerCase();
+ break;
+ }
}
- var printConfig = new PrintConfig(printOptions);
- printConfig.createPrintOptions().then(lang.hitch(this, function (results) {
- var templates = results.templates;
- var legendLayers = results.legendLayers;
-
- //add a text box so users can enter a custom title
- var titleNode = domConstruct.create("input", {
- id: "print_title",
- className: "printTitle",
- tabindex: "0",
- placeholder: this.config.i18n.tools.print.titlePrompt
- }, domConstruct.create("div"));
- domConstruct.place(titleNode, printDiv);
+ if (this.config.hasOwnProperty("tool_print_format")) {
+ this.format = this.config.tool_print_format.toLowerCase();
+ }
- if (has("print-legend")) {
- var legendNode = domConstruct.create("input", {
- id: "legend_ck",
- className: "checkbox",
- type: "checkbox",
- checked: false
- }, domConstruct.create("div", {
- "class": "checkbox"
- }));
+ if (has("print-legend")) {
+ legendNode = domConstruct.create("input", {
+ id: "legend_ck",
+ className: "checkbox",
+ type: "checkbox",
+ checked: false
+ }, domConstruct.create("div", {
+ "class": "checkbox"
+ }));
+ var labelNode = domConstruct.create("label", {
+ "for": "legend_ck",
+ "className": "checkbox",
+ "innerHTML": this.config.i18n.tools.print.legend
+ }, domConstruct.create("div"));
+ domConstruct.place(legendNode, printDiv);
+ domConstruct.place(labelNode, printDiv);
- var labelNode = domConstruct.create("label", {
- "for": "legend_ck",
- "className": "checkbox",
- "innerHTML": " " + this.config.i18n.tools.print.legend
- }, domConstruct.create("div"));
- domConstruct.place(legendNode, printDiv);
- domConstruct.place(labelNode, printDiv);
+ on(legendNode, "change", lang.hitch(this, function (arg) {
- on(legendNode, "change", lang.hitch(this, function (arg) {
- if (legendNode.checked && legendLayers.length > 0) {
+ if (legendNode.checked) {
+ var layers = arcgisUtils.getLegendLayers(this.config.response);
+ var legendLayers = array.map(layers, function (layer) {
+ return {
+ "layerId": layer.layer.id
+ };
+ });
+ if (legendLayers.length > 0) {
layoutOptions.legendLayers = legendLayers;
- } else {
- layoutOptions.legendLayers = [];
}
- array.forEach(this.print.templates, lang.hitch(this, function (template) {
+ array.forEach(print.templates, function (template) {
template.layoutOptions = layoutOptions;
- }));
- }));
+ });
- } else {
- domStyle.set("pageBody_print", "height", "90px");
- }
- var printOptions = {
- map: this.map,
- id: "printButton",
- url: this.config.helperServices.printTask.url
- };
- if(templates){
- printOptions.templates = templates;
+ } else {
+ array.forEach(print.templates, function (template) {
+ if (template.layoutOptions && template.layoutOptions.legendLayers) {
+ template.layoutOptions.legendLayers = [];
+ }
+ });
+ }
+ }));
+ }
+
+ require(["application/has-config!print-layouts?esri/request", "application/has-config!print-layouts?esri/tasks/PrintTemplate"], lang.hitch(this, function (esriRequest, PrintTemplate) {
+ if (!esriRequest && !PrintTemplate) {
+ //Use the default print templates
+ var templates = [{
+ layout: "Letter ANSI A Landscape",
+ layoutOptions: layoutOptions,
+ label: this.config.i18n.tools.print.layouts.label1 + " ( " + this.format + " )",
+ format: this.format
+ },
+ {
+ layout: "Letter ANSI A Portrait",
+ layoutOptions: layoutOptions,
+ label: this.config.i18n.tools.print.layouts.label2 + " ( " + this.format + " )",
+ format: this.format
+ },
+ {
+ layout: "Letter ANSI A Landscape",
+ layoutOptions: layoutOptions,
+ label: this.config.i18n.tools.print.layouts.label3 + " ( image )",
+ format: "PNG32"
+ },
+ {
+ layout: "Letter ANSI A Portrait",
+ layoutOptions: layoutOptions,
+ label: this.config.i18n.tools.print.layouts.label4 + " ( image )",
+ format: "PNG32"
+ }];
+
+ print = new Print({
+ map: this.map,
+ id: "printButton",
+ templates: templates,
+ url: this.config.helperServices.printTask.url
+ }, domConstruct.create("div"));
+ domConstruct.place(print.printDomNode, printDiv, "first");
+
+ print.startup();
+
+ deferred.resolve(true);
+ return;
}
- // Add a loading indicator to the Printing label
- esriBundle.widgets.print.NLS_printing = esriBundle.widgets.print.NLS_printing + " ";
- this.print = new Print(printOptions, domConstruct.create("div"));
- domConstruct.place(this.print.printDomNode, printDiv, "first");
+ esriRequest({
+ url: this.config.helperServices.printTask.url,
+ content: {
+ "f": "json"
+ },
+ "callbackParamName": "callback"
+ }).then(lang.hitch(this, function (response) {
+ var layoutTemplate, templateNames, mapOnlyIndex, templates;
+
+ layoutTemplate = array.filter(response.parameters, function (param, idx) {
+ return param.name === "Layout_Template";
+ });
- this.print.on("print-start", lang.hitch(this, function () {
- var printBox = dom.byId("print_title");
- if (printBox.value) {
- array.forEach(this.print.templates, lang.hitch(this, function (template) {
- template.layoutOptions.titleText = printBox.value;
- }));
+ if (layoutTemplate.length === 0) {
+ console.log("print service parameters name for templates must be \"Layout_Template\"");
+ return;
}
- }));
+ templateNames = layoutTemplate[0].choiceList;
- this.print.startup();
+ // remove the MAP_ONLY template then add it to the end of the list of templates
+ mapOnlyIndex = array.indexOf(templateNames, "MAP_ONLY");
+ if (mapOnlyIndex > -1) {
+ var mapOnly = templateNames.splice(mapOnlyIndex, mapOnlyIndex + 1)[0];
+ templateNames.push(mapOnly);
+ }
- }));
- deferred.resolve(true);
- return;
+ // create a print template for each choice
+ templates = array.map(templateNames, lang.hitch(this, function (name) {
+ var plate = new PrintTemplate();
+ plate.layout = plate.label = name;
+ plate.format = this.format;
+ plate.layoutOptions = layoutOptions;
+ return plate;
+ }));
+ print = new Print({
+ map: this.map,
+ templates: templates,
+ url: this.config.helperServices.printTask.url
+ }, domConstruct.create("div"));
+ domConstruct.place(print.printDomNode, printDiv, "first");
+ print.startup();
+ deferred.resolve(true);
+ }));
+ }));
}));
+
return deferred.promise;
},
- _addShare: function (tool, toolbar, panelClass) {
+
+ _addShare: function (tool, toolbar) {
//Add share links for facebook, twitter and direct linking.
//Add the measure widget to the toolbar.
var deferred = new Deferred();
if (has("share")) {
- var shareDiv = toolbar.createTool(tool, panelClass);
-
+ var shareDiv = domConstruct.create('div', {class:'pageBody'},toolbar.createTool(tool));//);
+
var shareDialog = new ShareDialog({
bitlyLogin: this.config.bitlyLogin,
bitlyKey: this.config.bitlyKey,
@@ -747,34 +1474,17 @@ define([
title: this.config.title,
summary: this.config.response.itemInfo.item.snippet || ""
}, shareDiv);
- domClass.add(shareDialog.domNode, "pageBody");
+ // domClass.add(shareDialog.domNode, "margin");
shareDialog.startup();
+ //domClass.add(dom.byId('_dialogNode'),'margin')
deferred.resolve(true);
} else {
deferred.resolve(false);
}
-
return deferred.promise;
-
},
- _getEditableLayers: function (layers) {
- var layerInfos = [];
- array.forEach(layers, lang.hitch(this, function (layer) {
-
- if (layer && layer.layerObject) {
- var eLayer = layer.layerObject;
- if (eLayer instanceof FeatureLayer && eLayer.isEditable()) {
- layerInfos.push({
- "featureLayer": eLayer
- });
- }
- }
- }));
- return layerInfos;
- },
-
_getBasemapGroup: function () {
//Get the id or owner and title for an organizations custom basemap group.
@@ -793,27 +1503,9 @@ define([
},
_createMapUI: function () {
- // Add map specific widgets like the Home and locate buttons. Also add the geocoder.
- if (has("home")) {
- domConstruct.create("div", {
- id: "panelHome",
- className: "icon-color tool",
- innerHTML: "
"
- }, dom.byId("panelTools"), 0);
- var home = new HomeButton({
- map: this.map
- }, dom.byId("btnHome"));
-
- if (!has("touch")) {
- //add a tooltip
- domAttr.set("btnHome", "data-title", this.config.i18n.tooltips.home);
- } else {
- //remove no-touch class from body
- domClass.remove(document.body, "no-touch");
-
- }
-
- home.startup();
+ if (!has("touch")) {
+ //remove no-touch class from body
+ domClass.remove(document.body, "no-touch");
}
require(["application/has-config!scalebar?esri/dijit/Scalebar"], lang.hitch(this, function (Scalebar) {
@@ -824,170 +1516,233 @@ define([
map: this.map,
scalebarUnit: this.config.units
});
-
}));
-
- if (has("locate")) {
- domConstruct.create("div", {
- id: "panelLocate",
- className: "icon-color tool",
- innerHTML: "
"
- }, dom.byId("panelTools"), 1);
- var geoLocate = new LocateButton({
- map: this.map,
- useTracking: this.config.locate_track
- }, dom.byId("btnLocate"));
- if (!has("touch")) {
- //add a tooltip
- domAttr.set("btnLocate", "data-title", this.config.i18n.tooltips.locate);
- }
-
- geoLocate.startup();
-
- }
-
//Add the location search widget
- require(["application/has-config!search?esri/dijit/Search", "application/has-config!search?esri/tasks/locator"], lang.hitch(this, function (Search, Locator) {
+ require(["application/has-config!search?esri/dijit/Search",
+ "application/has-config!search?esri/tasks/locator"],
+ lang.hitch(this, function (Search, Locator) {
if (!Search && !Locator) {
//add class so we know we don't have to hide title since search isn't visible
domClass.add("panelTop", "no-search");
return;
}
- var searchOptions = {
+ var options = {
map: this.map,
- useMapExtent: this.config.searchExtent,
- itemData: this.config.response.itemInfo.itemData
+ addLayersFromMap: false,
+ enableSearchingAll: true,
+ activeSourceIndex: "All"
};
- if (this.config.searchConfig) {
- searchOptions.applicationConfiguredSources = this.config.searchConfig.sources || [];
- } else {
- var configuredSearchLayers = (this.config.searchLayers instanceof Array) ? this.config.searchLayers : JSON.parse(this.config.searchLayers);
- searchOptions.configuredSearchLayers = configuredSearchLayers;
- searchOptions.geocoders = this.config.locationSearch ? this.config.helperServices.geocode : [];
- }
- var searchSources = new SearchSources(searchOptions);
- var createdOptions = searchSources.createOptions();
-
- if (this.config.searchConfig && this.config.searchConfig.activeSourceIndex) {
- createdOptions.activeSourceIndex = this.config.searchConfig.activeSourceIndex;
- }
-
- var search = new Search(createdOptions, domConstruct.create("div", {
+ var searchLayers = false;
+ var search = new Search(options, domConstruct.create("div", {
id: "search"
}, "mapDiv"));
+ var defaultSources = [];
- search.on("select-result", lang.hitch(this, function () {
- //if edit tool is enabled we'll have to delete/create
- //so info window behaves correctly.
- on.once(this.map.infoWindow, "hide", lang.hitch(this, function () {
- search.clearGraphics();
- if (this.editor) {
- this._destroyEditor();
- this._createEditor();
+ //setup geocoders defined in common config
+ if (this.config.helperServices.geocode && this.config.locationSearch) {
+ var geocoders = lang.clone(this.config.helperServices.geocode);
+ array.forEach(geocoders, lang.hitch(this, function (geocoder) {
+ if (geocoder.url.indexOf(".arcgis.com/arcgis/rest/services/World/GeocodeServer") > -1) {
+
+ geocoder.hasEsri = true;
+ geocoder.locator = new Locator(geocoder.url);
+
+ geocoder.singleLineFieldName = "SingleLine";
+
+ geocoder.name = geocoder.name || "Esri World Geocoder";
+
+ if (this.config.searchExtent) {
+ geocoder.searchExtent = this.map.extent;
+ geocoder.localSearchOptions = {
+ minScale: 300000,
+ distance: 50000
+ };
+ }
+ defaultSources.push(geocoder);
+ } else if (esriLang.isDefined(geocoder.singleLineFieldName)) {
+
+ //Add geocoders with a singleLineFieldName defined
+ geocoder.locator = new Locator(geocoder.url);
+
+ defaultSources.push(geocoder);
}
}));
+ }
+ //add configured search layers to the search widget
+ var configuredSearchLayers = (this.config.searchLayers instanceof Array) ? this.config.searchLayers : JSON.parse(this.config.searchLayers);
+
+ array.forEach(configuredSearchLayers, lang.hitch(this, function (layer) {
+
+ var mapLayer = this.map.getLayer(layer.id);
+ if (mapLayer) {
+ var source = {};
+ source.featureLayer = mapLayer;
+
+ if (layer.fields && layer.fields.length && layer.fields.length > 0) {
+ source.searchFields = layer.fields;
+ source.displayField = layer.fields[0];
+ source.outFields = ["*"];
+ searchLayers = true;
+ defaultSources.push(source);
+ if (mapLayer.infoTemplate) {
+ source.infoTemplate = mapLayer.infoTemplate;
+ }
+ }
+ }
}));
+
+ //Add search layers defined on the web map item
+ if (this.config.response.itemInfo.itemData &&
+ this.config.response.itemInfo.itemData.applicationProperties &&
+ this.config.response.itemInfo.itemData.applicationProperties.viewing &&
+ this.config.response.itemInfo.itemData.applicationProperties.viewing.search) {
+
+ var searchOptions = this.config.response.itemInfo.itemData.applicationProperties.viewing.search;
+
+ array.forEach(searchOptions.layers, lang.hitch(this, function (searchLayer) {
+ //we do this so we can get the title specified in the item
+ var operationalLayers = this.config.itemInfo.itemData.operationalLayers;
+ var layer = null;
+ array.some(operationalLayers, function (opLayer) {
+ if (opLayer.id === searchLayer.id) {
+ layer = opLayer;
+ return true;
+ }
+ });
+
+ if (layer && layer.hasOwnProperty("url")) {
+ var source = {};
+ var url = layer.url;
+ var name = layer.title || layer.name;
+
+ if (esriLang.isDefined(searchLayer.subLayer)) {
+ url = url + "/" + searchLayer.subLayer;
+ array.some(layer.layerObject.layerInfos, function (info) {
+ if (info.id == searchLayer.subLayer) {
+ name += " - " + layer.layerObject.layerInfos[searchLayer.subLayer].name;
+ return true;
+ }
+ });
+ }
+
+ source.featureLayer = new FeatureLayer(url);
+
+ source.name = name;
+
+ source.exactMatch = searchLayer.field.exactMatch;
+ source.displayField = searchLayer.field.name;
+ source.searchFields = [searchLayer.field.name];
+ source.placeholder = searchOptions.hintText;
+ defaultSources.push(source);
+ searchLayers = true;
+ }
+
+ }));
+ }
+
+ defaultSources.forEach(function(source) {
+ if(!source.placeholder || source.placeholder === undefined || source.placeholder ==="") {
+ if(source.featureLayer && source.featureLayer.name) {
+ source.placeholder = i18n.searchEnterCriteria+" "+source.featureLayer.name;
+ }
+ else {
+ source.placeholder = i18n.searchPlaceholder;
+ }
+ }
+ });
+ search.set("sources", defaultSources);
+
search.startup();
if (search && search.domNode) {
domConstruct.place(search.domNode, "panelGeocoder");
- }
- // update the search placeholder text color and dropdown
- // to match the icon text
- if(this.config.icons === "black"){
- query(".arcgisSearch .searchIcon").style("color", "#000");
- domClass.add(dom.byId("search_input"),"dark");
- }
+
+ var esriIconDownArrowNode = dojo.query(".searchIcon.esri-icon-down-arrow")[0];
+ if(esriIconDownArrowNode)
+ {
+ domClass.remove(esriIconDownArrowNode, "searchIcon esri-icon-down-arrow");
- }));
+ esriIconDownArrowNode.innerHTML =
+ ' ';
+ }
+ var searchInput = dojo.query(".searchInput")[0];
+ dojo.setAttr(searchInput, 'role', 'search');
- //Feature Search or find (if no search widget)
- if ((this.config.find || (this.config.customUrlLayer.id !== null && this.config.customUrlLayer.fields.length > 0 && this.config.customUrlParam !== null))) {
- require(["esri/dijit/Search"], lang.hitch(this, function (Search) {
- var source = null,
- value = null,
- searchLayer = null;
-
- var urlObject = urlUtils.urlToObject(document.location.href);
- urlObject.query = urlObject.query || {};
- urlObject.query = esriLang.stripTags(urlObject.query);
- var customUrl = null;
- for(var prop in urlObject.query){
- if(urlObject.query.hasOwnProperty(prop)){
- if(prop.toUpperCase() === this.config.customUrlParam.toUpperCase()){
- customUrl = prop;
- }
- }
+ var esriIconZoomNode = dojo.query(".searchIcon.esri-icon-search")[0];
+ if(esriIconZoomNode)
+ {
+ domClass.remove(esriIconZoomNode, "searchIcon esri-icon-search");
+ esriIconZoomNode.innerHTML =
+ ' ';
}
- //Support find or custom url param
- if (this.config.find) {
- value = decodeURIComponent(this.config.find);
- } else if (customUrl){
-
- value = urlObject.query[customUrl];
- searchLayer = this.map.getLayer(this.config.customUrlLayer.id);
- if (searchLayer) {
-
- var searchFields = this.config.customUrlLayer.fields[0].fields;
- source = {
- exactMatch: true,
- outFields: ["*"],
- featureLayer: searchLayer,
- displayField: searchFields[0],
- searchFields: searchFields
- };
- }
+ var esriIconCloseNode = dojo.query(".searchIcon.esri-icon-close.searchClose")[0];
+ if(esriIconCloseNode) {
+ domClass.remove(esriIconCloseNode, "searchIcon esri-icon-close");
+ esriIconCloseNode.innerHTML =
+ ' ';
}
- var urlSearch = new Search({
- map: this.map
- });
+ }
- if (source) {
- urlSearch.set("sources", [source]);
+ var emptySearchItems = query('.searchInputGroup > input[type="text"] ');
+ emptySearchItems.forEach(function(s) {
+ if(domAttr.get(s, "placeholder") ==='')
+ {
+ domAttr.set(s, "placeholder", i18n.searchPlaceholder);
+ domAttr.set(s, "title", i18n.searchPlaceholder);
}
- urlSearch.on("load", lang.hitch(this, function () {
- urlSearch.search(value).then(lang.hitch(this, function () {
- on.once(this.map.infoWindow, "hide", lang.hitch(this, function () {
- //urlSearch.clear();
- urlSearch.destroy();
- if (this.editor) {
- this._destroyEditor();
- this._createEditor();
+ });
+
+
+ var containerNode = dojo.query('#search [data-dojo-attach-point=containerNode]');
+ if(containerNode && containerNode.length > 0) {
+ var containerNodeObserver = new MutationObserver(function(mutations) {
+ mutations.forEach(function(mutation) {
+ //console.log(mutation.target);
+ var box = dojo.query('#search .searchInputGroup')[0];
+ if(dojo.hasClass(mutation.target, 'showNoResults'))
+ {
+ var nrText = '';
+ var h = query('#search .noResultsText');
+ if(h && h.length>0) {
+ nrText = query('#search .noResultsHeader')[0].innerHTML+': '+h[0].innerHTML;
+ } else {
+ h = query('#search .noValueText');
+ if(h && h.length > 0) {
+ nrText = h[0].innerHTML;
+ }
}
- }));
- }));
- }));
- urlSearch.startup();
+ //console.log(nrText);
+ //console.log(mutation.target);
+ dojo.attr(box, 'aria-label', nrText);
+ dojo.attr(box, 'tabindex', 0);
+ box.focus();
+ }
+ else {
+ dojo.removeAttr(box, 'tabindex');
+ dojo.removeAttr(box, 'aria-label');
+ }
+ });
+ });
- }));
- }
+ var observerCfg = { attributes: true, childList: false, characterData: false };
- //create the tools
- this._createUI();
+ containerNodeObserver.observe(containerNode[0], observerCfg);
+ }
- },
- _setColor: function (color) {
- //Convert the string color from the config file to rgba if supported.
- var rgb = Color.fromHex(color).toRgb();
- var outputColor = null;
- if (has("ie") < 9) {
- outputColor = color;
- } else {
- //rgba supported so add
- rgb.push(0.9);
- outputColor = Color.fromArray(rgb);
+ }));
- }
- return outputColor;
+ //create the tools
+ this._createUI();
},
+
_updateTheme: function () {
- //Update the app to use the configured color scheme.
+
//Set the background color using the configured theme value
query(".bg").style("backgroundColor", this.theme.toString());
query(".esriPopup .pointer").style("backgroundColor", this.theme.toString());
@@ -1008,20 +1763,76 @@ define([
query(".icon-color").style("color", "#000");
}
+ var styleSheetList = document.styleSheets;
+ var styleCss = null;
+ for(i=0; i0) {
+ styleCss = css;
+ break;
+ }
+ }
+
+ if(styleCss) {
+ for(i=0; i= 0) {
+ rule.style.backgroundColor = this._rgbaColor(this.hoverColor);
+ }
+ // if(rule.selectorText.indexOf('.goThereHint') >= 0) {
+ // rule.style.backgroundColor = this._rgbaColor(this.hoverColor);
+ // }
+ //focus
+ if(rule.selectorText.indexOf(':focus') >= 0) {
+ // rule.style.outlineStyle = 'none';
+ // rule.style.outlineColor = 'transparent';
+ // rule.style.boxShadow = '0 0 0 2px '+this.focusColor+' inset';
+ rule.style.outlineColor = this._rgbaColor(this.focusColor);
+ }
+ if(rule.selectorText.indexOf('.goThereHint') >= 0) {
+ rule.style.borderColor = this._rgbaColor(this.focusColor);
+ //rule.style.boxShadow = "3px 3px 10px "+this._rgbaColor(this.focusColor);
+ }
+ //active
+ if(rule.selectorText.indexOf('.activeMarker') >= 0 ||
+ //rule.selectorText.indexOf('.goThereHint') >= 0 ||
+ rule.selectorText.indexOf('dijitSplitterThumb') >= 0) {
+ rule.style.backgroundColor = this._rgbaColor(this.activeColor);
+ rule.style.outlineStyle = 'none';
+ rule.style.outlineColor = 'transparent';
+ rule.style.boxShadow = '0 0 15px 15px '+this.activeColor+' inset';
+ }
+ }
+ }
+ }
+ //debugger;
},
- _adjustPopupSize: function () {
- //Set the popup size to be half the widget and .35% of the map height
+ _rgbaColor: function(color) {
+ return 'rgb('+color.r+', '+color.g+', '+color.b+')';
+ },
+
+ _checkExtent: function () {
+ var pt = this.map.extent.getCenter();
+ if (this.mapExt && !this.initExt.contains(pt)) {
+ this.map.setExtent(this.mapExt);
+ } else {
+ this.mapExt = this.map.extent;
+ }
+ },
+
+ _adjustPopupSize: function () {
if (!this.map) {
return;
}
-
var box = domGeometry.getContentBox(this.map.container);
var width = 270,
- height = 300,
- newWidth = Math.round(box.w * 0.50),
- newHeight = Math.round(box.h * 0.35);
+ height = 300,
+ newWidth = Math.round(box.w * 0.50),
+ newHeight = Math.round(box.h * 0.35);
if (newWidth < width) {
width = newWidth;
}
@@ -1029,69 +1840,186 @@ define([
height = newHeight;
}
this.map.infoWindow.resize(width, height);
- on(this.map.infoWindow, "show", lang.hitch(this, function () {
- domClass.add(document.body, "noscroll");
- }));
- on(this.map.infoWindow, "hide", lang.hitch(this, function () {
- domClass.remove(document.body, "noscroll");
- }));
-
},
+
_createWebMap: function (itemInfo) {
window.config = this.config;
- itemInfo = this._setExtent(itemInfo);
- var mapOptions = {};
- mapOptions = this._setLevel(mapOptions);
- mapOptions = this._setCenter(mapOptions);
+ var options = {};
+ //specify center and zoom if provided as url params
+ if (this.config.level) {
+ options.zoom = this.config.level;
+ }
+ if (this.config.center) {
+ var points = this.config.center.split(",");
+ if (points && points.length === 2) {
+ options.center = [parseFloat(points[0]), parseFloat(points[1])];
+ }
+
+ }
// create a map based on the input web map id
arcgisUtils.createMap(itemInfo, "mapDiv", {
- mapOptions: mapOptions,
+ mapOptions: options,
editable: has("edit"),
//is the app editable
usePopupManager: true,
- layerMixins: this.config.layerMixins,
bingMapsKey: this.config.bingKey
}).then(lang.hitch(this, function (response) {
+ var mapDiv = document.querySelector('#mapDiv');
+ on(mapDiv, 'keydown', lang.hitch(this, function(evn){
+ if(!document.querySelector(':focus') || document.querySelector(':focus').id !== "mapDiv") return;
+ switch(evn.keyCode) {
+ case 40 : //down
+ this.map._fixedPan(0, this.map.height * 0.0135);
+ evn.preventDefault();
+ evn.stopPropagation();
+ break;
+ case 38 : //up
+ this.map._fixedPan(0, this.map.height * -0.0135);
+ evn.preventDefault();
+ evn.stopPropagation();
+ break;
+ case 37 : //left
+ this.map._fixedPan(this.map.width * -0.0135, 0);
+ evn.preventDefault();
+ evn.stopPropagation();
+ break;
+ case 39 : //right
+ this.map._fixedPan(this.map.width * 0.0135, 0);
+ evn.preventDefault();
+ evn.stopPropagation();
+ break;
+ case 33 : //pgup
+ this.map._fixedPan(this.map.width * 0.0135, this.map.height * -0.0135);
+ evn.preventDefault();
+ evn.stopPropagation();
+ break;
+ case 34 : //pgdn
+ this.map._fixedPan(this.map.width * 0.0135, this.map.height * 0.0135);
+ evn.preventDefault();
+ evn.stopPropagation();
+ break;
+ case 35 : //end
+ this.map._fixedPan(this.map.width * -0.0135, this.map.height * 0.0135);
+ evn.preventDefault();
+ evn.stopPropagation();
+ break;
+ case 36 : //home
+ this.map._fixedPan(this.map.width * -0.0135, this.map.height * -0.0135);
+ evn.preventDefault();
+ evn.stopPropagation();
+ break;
+ }
+ }));
+ on(mapDiv, 'keypress', lang.hitch(this, function(evn){
+ if(!document.querySelector(':focus') || document.querySelector(':focus').id !== "mapDiv") return;
+ evn.preventDefault();
+ evn.stopPropagation();
+ if((evn.keyCode === 43) && !evn.ctrlKey && !evn.altKey) // Shift-'+'
+ {
+ this.map.setLevel(this.map.getLevel() + 1);
+ }
+ if((evn.keyCode === 45) && !evn.ctrlKey && !evn.altKey) // Shift-'-'
+ {
+ this.map.setLevel(this.map.getLevel() - 1);
+ }
+ }));
+
this.map = response.map;
-
domClass.add(this.map.infoWindow.domNode, "light");
-
this._updateTheme();
+ var title;
+ if (this.config.title === null || this.config.title === "") {
+ title = response.itemInfo.item.title + " - " + this.config.i18n.wcagViewer;
+ } else {
+ title = this.config.title+': '+response.itemInfo.item.title + " - " + this.config.i18n.wcagViewer;
+ }
+
+ if(this.config.altMapText !== undefined) {
+ var altMapText = esriLang.stripTags(this.config.altMapText);
+ domAttr.set(this.map.container, "aria-label", altMapText);
+ }
+
//Add a logo if provided
if (this.config.logo) {
- domConstruct.create("div", {
+ var altText = this.config.logoAltText;
+ if(!altText || altText === '')
+ altText = title;
+ var panelLogo = domConstruct.create("div", {
id: "panelLogo",
- innerHTML: " >"
- }, dom.byId("panelTitle"), "first");
- domClass.add("panelTop", "largerTitle");
+ TabIndex:0,
+ innerHTML: " >"
+ }, dom.byId("panelTitle"));//, "first");
+ //domClass.add("panelTop", "largerTitle");
+ dojo.place(panelLogo, dojo.byId('panelText'), 'before');
}
//Set the application title
- this.map = response.map;
+ //this.map = response.map;
//Set the title - use the config value if provided.
- var title;
+ //var title = (this.config.title === null) ? response.itemInfo.item.title : this.config.title;
+
+ //if title is short make title area smaller
+ if (title && title.length && title.length === 0) {
+ domClass.add("panelTop", "smallerTitle");
+ } else if (title && title.length && title.length <= 20 && !this.config.logo) {
+ domClass.add("panelTop", "smallerTitle");
+ }
+
+ document.title = title;
if (this.config.title === null || this.config.title === "") {
- title = response.itemInfo.item.title;
- } else {
- title = this.config.title;
+ dom.byId("panelText").innerHTML = response.itemInfo.item.title;
+ }
+ else {
+ dom.byId("panelText").innerHTML = this.config.title;
}
+ domAttr.set(dom.byId("panelText"),"TabIndex",0);
this.config.title = title;
- document.title = esriLang.stripTags(title);
- dom.byId("title").innerHTML = title;
+ if(!response.itemInfo.itemData)
+ response.itemInfo.itemData = {};
+ if(!response.itemInfo.itemData.applicationProperties)
+ response.itemInfo.itemData.applicationProperties = {};
+ if(!response.itemInfo.itemData.applicationProperties.viewing)
+ response.itemInfo.itemData.applicationProperties.viewing = {};
+ if(!response.itemInfo.itemData.applicationProperties.viewing.search)
+ response.itemInfo.itemData.applicationProperties.viewing.search = { hintText: i18n.searchPlaceholder };
+ this.config.response = response;
+ window.config = this.config;
- //Set subtitle if provided
- if (this.config.subtitle) {
- dom.byId("subtitle").innerHTML = this.config.subtitle;
- } else {
- domClass.add("title", "nosubtitle");
+ if (this.initExt !== null) {
+ this.map.setExtent(this.initExt);
}
- this.config.response = response;
+ window.initExt = this.initExt = this.map.extent;
+
+ on.once(this.map, "extent-change", lang.hitch(this, function() {
+ navDeferred.then(lang.hitch(this, function (results) {
+ this._checkExtent();
+ var homeButton = document.querySelector(".HomeButton input[type='image']");
+ if(homeButton)
+ homeButton.click();
+ }));
+
+ // legend heades missing
+ var dojoxGridRowTables = query('.dojoxGridRowTable');
+ if(dojoxGridRowTables)
+ {
+ dojoxGridRowTables.forEach(function(table) {
+ dojo.removeAttr(table,"role");
+ });
+ }
+
+ }));
+
+ on(this.map, "extent-change", function() {
+ var imgs = this.container.querySelectorAll("img");
+ for(i=0; i 0 && this.config.itemInfo && this.config.itemInfo.item && this.config.itemInfo.item.extent) {
- this.config.itemInfo.item.extent = [
- [
- parseFloat(this.config.application_extent[0][0]), parseFloat(this.config.application_extent[0][1])
- ],
- [
- parseFloat(this.config.application_extent[1][0]), parseFloat(this.config.application_extent[1][1])
- ]
- ];
- }
- // Set the geometry helper service to be the app default.
- if (this.config.helperServices && this.config.helperServices.geometry && this.config.helperServices.geometry.url) {
- esriConfig.defaults.geometryService = new GeometryService(this.config.helperServices.geometry.url);
- }
- },
- _mixinAll: function() {
- /*
+ // We have all we need, let's set up a few things
+ this._completeApplication();
+ deferred.resolve(this.config);
+ }), deferred.reject);
+ }), deferred.reject);
+ }));
+ // return promise
+ return deferred.promise;
+ },
+ _completeApplication: function () {
+ // ArcGIS.com allows you to set an application extent on the application item. Overwrite the
+ // existing web map extent with the application item extent when set.
+ if (this.config.appid && this.config.application_extent && this.config.application_extent.length > 0 && this.config.itemInfo && this.config.itemInfo.item && this.config.itemInfo.item.extent) {
+ this.config.itemInfo.item.extent = [
+ [
+ parseFloat(this.config.application_extent[0][0]), parseFloat(this.config.application_extent[0][1])
+ ],
+ [
+ parseFloat(this.config.application_extent[1][0]), parseFloat(this.config.application_extent[1][1])
+ ]
+ ];
+ }
+ // Set the geometry helper service to be the app default.
+ if (this.config.helperServices && this.config.helperServices.geometry && this.config.helperServices.geometry.url) {
+ esriConfig.defaults.geometryService = new GeometryService(this.config.helperServices.geometry.url);
+ }
+ },
+ _mixinAll: function () {
+ /*
mix in all the settings we got!
{} <- i18n <- organization <- application <- group info <- group items <- webmap <- custom url params <- standard url params.
*/
- lang.mixin(this.config, this.i18nConfig, this.orgConfig, this.appConfig, this.groupInfoConfig, this.groupItemConfig, this.itemConfig, this.customUrlConfig, this.urlConfig);
- },
- _createPortal: function() {
- var deferred = new Deferred();
- if (this.templateConfig.queryForGroupInfo || this.templateConfig.queryForGroupItems) {
- this.portal = new esriPortal.Portal(this.config.sharinghost);
- this.portal.on("load", function() {
- deferred.resolve();
- });
- } else {
- deferred.resolve();
- }
- return deferred.promise;
- },
- _getUrlParamValues: function(items) {
- // retrieves only the items specified from the URL object.
- var urlObject = this.urlObject;
- var obj = {};
- if (urlObject && urlObject.query && items && items.length) {
- for (var i = 0; i < items.length; i++) {
- var item = urlObject.query[items[i]];
- if (item) {
- if (typeof item === "string") {
- switch (item.toLowerCase()) {
- case "true":
- obj[items[i]] = true;
- break;
- case "false":
- obj[items[i]] = false;
- break;
- default:
- obj[items[i]] = item;
- }
- } else {
- obj[items[i]] = item;
- }
- }
- }
- }
- return obj;
- },
- _createUrlParamsObject: function() {
- var urlObject,
- url;
- // retrieve url parameters. Templates all use url parameters to determine which arcgis.com
- // resource to work with.
- // Map templates use the webmap param to define the webmap to display
- // Group templates use the group param to provide the id of the group to display.
- // appid is the id of the application based on the template. We use this
- // id to retrieve application specific configuration information. The configuration
- // information will contain the values the user selected on the template configuration
- // panel.
- url = document.location.href;
- urlObject = urlUtils.urlToObject(url);
- urlObject.query = urlObject.query || {};
- // remove any HTML tags from query item
- urlObject.query = esriLang.stripTags(urlObject.query);
- return urlObject;
- },
- _initializeApplication: function() {
- // If this app is hosted on an Esri environment.
- if (this.templateConfig.esriEnvironment) {
- var appLocation, instance;
- // Check to see if the app is hosted or a portal. If the app is hosted or a portal set the
- // sharing url and the proxy. Otherwise use the sharing url set it to arcgis.com.
- // We know app is hosted (or portal) if it has /apps/ or /home/ in the url.
- appLocation = location.pathname.indexOf("/apps/");
- if (appLocation === -1) {
- appLocation = location.pathname.indexOf("/home/");
- }
- // app is hosted and no sharing url is defined so let's figure it out.
- if (appLocation !== -1) {
- // hosted or portal
- instance = location.pathname.substr(0, appLocation); //get the portal instance name
- this.config.sharinghost = location.protocol + "//" + location.host + instance;
- this.config.proxyurl = location.protocol + "//" + location.host + instance + "/sharing/proxy";
- }
- }
- arcgisUtils.arcgisUrl = this.config.sharinghost + "/sharing/rest/content/items";
- // Define the proxy url for the app
- if (this.config.proxyurl) {
- esriConfig.defaults.io.proxyUrl = this.config.proxyurl;
- esriConfig.defaults.io.alwaysUseProxy = false;
- }
- },
- _checkSignIn: function() {
- var deferred, signedIn, oAuthInfo;
- deferred = new Deferred();
- //If there's an oauth appid specified register it
- if (this.config.oauthappid) {
- oAuthInfo = new ArcGISOAuthInfo({
- appId: this.config.oauthappid,
- portalUrl: this.config.sharinghost,
- popup: true
- });
- IdentityManager.registerOAuthInfos([oAuthInfo]);
+ lang.mixin(this.config, this.i18nConfig, this.orgConfig, this.appConfig, this.groupInfoConfig, this.groupItemConfig, this.displayItemConfig, this.customUrlConfig, this.urlConfig);
+ },
+ _createPortal: function () {
+ var deferred = new Deferred();
+ if (this.templateConfig.queryForGroupInfo || this.templateConfig.queryForGroupItems) {
+ this.portal = new esriPortal.Portal(this.config.sharinghost);
+ this.portal.on("load", function () {
+ deferred.resolve();
+ });
+ } else {
+ deferred.resolve();
+ }
+ return deferred.promise;
+ },
+ _getUrlParamValues: function (items) {
+ // retreives only the items specified from the URL object.
+ var urlObject = this.urlObject,
+ obj = {},
+ i;
+ if (urlObject && urlObject.query && items && items.length) {
+ for (i = 0; i < items.length; i++) {
+ if (urlObject.query[items[i]]) {
+ var item = urlObject.query[items[i]];
+ obj[items[i]] = item === "true" || (item == "false" ? false : item);
+ }
+ }
+ }
+ return obj;
+ },
+ _createUrlParamsObject: function () {
+ var urlObject,
+ url;
+ // retrieve url parameters. Templates all use url parameters to determine which arcgis.com
+ // resource to work with.
+ // Map templates use the webmap param to define the webmap to display
+ // Group templates use the group param to provide the id of the group to display.
+ // appid is the id of the application based on the template. We use this
+ // id to retrieve application specific configuration information. The configuration
+ // information will contain the values the user selected on the template configuration
+ // panel.
+ url = document.location.href;
+ urlObject = urlUtils.urlToObject(url);
+ urlObject.query = urlObject.query || {};
+ // remove any HTML tags from query item
+ urlObject.query = esriLang.stripTags(urlObject.query);
+ return urlObject;
+ },
+ _initializeApplication: function () {
+ // If this app is hosted on an Esri environment.
+ if (this.templateConfig.esriEnvironment) {
+ var appLocation, instance;
+ // Check to see if the app is hosted or a portal. If the app is hosted or a portal set the
+ // sharing url and the proxy. Otherwise use the sharing url set it to arcgis.com.
+ // We know app is hosted (or portal) if it has /apps/ or /home/ in the url.
+ appLocation = location.pathname.indexOf("/apps/");
+ if (appLocation === -1) {
+ appLocation = location.pathname.indexOf("/home/");
+ }
+ // app is hosted and no sharing url is defined so let's figure it out.
+ if (appLocation !== -1) {
+ // hosted or portal
+ instance = location.pathname.substr(0, appLocation); //get the portal instance name
+ this.config.sharinghost = location.protocol + "//" + location.host + instance;
+ this.config.proxyurl = location.protocol + "//" + location.host + instance + "/sharing/proxy";
+ }
+ }
+ arcgisUtils.arcgisUrl = this.config.sharinghost + "/sharing/rest/content/items";
+ // Define the proxy url for the app
+ if (this.config.proxyurl) {
+ esriConfig.defaults.io.proxyUrl = this.config.proxyurl;
+ esriConfig.defaults.io.alwaysUseProxy = false;
+ }
+ },
+ _checkSignIn: function () {
+ var deferred, signedIn, oAuthInfo;
+ deferred = new Deferred();
+ //If there's an oauth appid specified register it
+ if (this.config.oauthappid) {
+ oAuthInfo = new ArcGISOAuthInfo({
+ appId: this.config.oauthappid,
+ portalUrl: this.config.sharinghost,
+ popup: true
+ });
+ IdentityManager.registerOAuthInfos([oAuthInfo]);
+ }
+ // check sign-in status
+ signedIn = IdentityManager.checkSignInStatus(this.config.sharinghost + "/sharing");
+ // resolve regardless of signed in or not.
+ signedIn.promise.always(function () {
+ deferred.resolve();
+ });
+ return deferred.promise;
+ },
+
+ _getLocalization: function () {
+ var deferred, dirNode, classes, rtlClasses;
+ deferred = new Deferred();
+ if (this.templateConfig.queryForLocale) {
+ require(["dojo/i18n!application/nls/resources"], lang.hitch(this, function (appBundle) {
+ // Get the localization strings for the template and store in an i18n variable. Also determine if the
+ // application is in a right-to-left language like Arabic or Hebrew.
+ this.i18nConfig.i18n = appBundle || {};
+ // Bi-directional language support added to support right-to-left languages like Arabic and Hebrew
+ // Note: The map must stay ltr
+ this.i18nConfig.i18n.direction = "ltr";
+ array.some(["ar", "he"], lang.hitch(this, function (l) {
+ if (kernel.locale.indexOf(l) !== -1) {
+ this.i18nConfig.i18n.direction = "rtl";
+ return true;
}
- // check sign-in status
- signedIn = IdentityManager.checkSignInStatus(this.config.sharinghost + "/sharing");
- // resolve regardless of signed in or not.
- signedIn.promise.always(function() {
- deferred.resolve();
+ return false;
+ }));
+ // add a dir attribute to the html tag. Then you can add special css classes for rtl languages
+ dirNode = document.getElementsByTagName("html")[0];
+ classes = dirNode.className;
+ if (this.i18nConfig.i18n.direction === "rtl") {
+ // need to add support for dj_rtl.
+ // if the dir node is set when the app loads dojo will handle.
+ dirNode.setAttribute("dir", "rtl");
+ rtlClasses = " esriRTL dj_rtl dijitRtl " + classes.replace(/ /g, "-rtl ");
+ dirNode.className = lang.trim(classes + rtlClasses);
+ } else {
+ dirNode.setAttribute("dir", "ltr");
+ domClass.add(dirNode, "esriLTR");
+ }
+ deferred.resolve(appBundle);
+ }));
+ } else {
+ deferred.resolve();
+ }
+ return deferred.promise;
+ },
+ queryGroupItems: function (options) {
+ var deferred = new Deferred(),
+ error, defaultParams, params;
+ // If we want to get the group info
+ if (this.templateConfig.queryForGroupItems) {
+ if (this.config.group) {
+ // group params
+ defaultParams = {
+ q: "group:\"${groupid}\" AND -type:\"Code Attachment\"",
+ sortField: "modified",
+ sortOrder: "desc",
+ num: 9,
+ start: 0,
+ f: "json"
+ };
+ // mixin params
+ params = lang.mixin(defaultParams, this.templateConfig.groupParams, options);
+ // place group ID
+ if (params.q) {
+ params.q = string.substitute(params.q, {
+ groupid: this.config.group
});
- return deferred.promise;
- },
- _queryLocalization: function() {
- var deferred, dirNode, classes, rtlClasses;
- deferred = new Deferred();
- if (this.templateConfig.queryForLocale) {
- require(["dojo/i18n!application/nls/resources"], lang.hitch(this, function(appBundle) {
- var cfg = {};
- // Get the localization strings for the template and store in an i18n variable. Also determine if the
- // application is in a right-to-left language like Arabic or Hebrew.
- cfg.i18n = appBundle || {};
- // Bi-directional language support added to support right-to-left languages like Arabic and Hebrew
- // Note: The map must stay ltr
- cfg.i18n.direction = "ltr";
- array.some(["ar", "he"], lang.hitch(this, function(l) {
- if (kernel.locale.indexOf(l) !== -1) {
- cfg.i18n.direction = "rtl";
- return true;
- }
- return false;
- }));
- // add a dir attribute to the html tag. Then you can add special css classes for rtl languages
- dirNode = document.getElementsByTagName("html")[0];
- classes = dirNode.className + " ";
- if (cfg.i18n.direction === "rtl") {
- // need to add support for dj_rtl.
- // if the dir node is set when the app loads dojo will handle.
- dirNode.setAttribute("dir", "rtl");
- rtlClasses = " esriRTL dj_rtl dijitRtl " + classes.replace(/ /g, "-rtl ");
- dirNode.className = lang.trim(classes + rtlClasses);
- } else {
- dirNode.setAttribute("dir", "ltr");
- domClass.add(dirNode, "esriLTR");
- }
- this.i18nConfig = cfg;
- deferred.resolve(cfg);
- }));
- } else {
- deferred.resolve();
- }
- return deferred.promise;
- },
- queryGroupItems: function(options) {
- var deferred = new Deferred(),
- error, defaultParams, params;
- // If we want to get the group info
- if (this.templateConfig.queryForGroupItems) {
- if (this.config.group) {
- // group params
- defaultParams = {
- q: "group:\"${groupid}\" AND -type:\"Code Attachment\"",
- sortField: "modified",
- sortOrder: "desc",
- num: 9,
- start: 0,
- f: "json"
- };
- // mixin params
- params = lang.mixin(defaultParams, this.templateConfig.groupParams, options);
- // place group ID
- if (params.q) {
- params.q = string.substitute(params.q, {
- groupid: this.config.group
- });
- }
- // get items from the group
- this.portal.queryItems(params).then(lang.hitch(this, function(response) {
- var cfg = {};
- cfg.groupItems = response;
- this.groupItemConfig = cfg;
- deferred.resolve(cfg);
- }), function(error) {
- deferred.reject(error);
- });
- } else {
- error = new Error("Group undefined.");
- deferred.reject(error);
- }
- } else {
- // just resolve
- deferred.resolve();
- }
- return deferred.promise;
- },
- queryGroupInfo: function() {
- var deferred = new Deferred(),
- error, params;
- // If we want to get the group info
- if (this.templateConfig.queryForGroupInfo) {
- if (this.config.group) {
- // group params
- params = {
- q: "id:\"" + this.config.group + "\"",
- f: "json"
- };
- this.portal.queryGroups(params).then(lang.hitch(this, function(response) {
- var cfg = {};
- cfg.groupInfo = response;
- this.groupInfoConfig = cfg;
- deferred.resolve(cfg);
- }), function(error) {
- deferred.reject(error);
- });
- } else {
- error = new Error("Group undefined.");
- deferred.reject(error);
- }
- } else {
- // just resolve
- deferred.resolve();
- }
- return deferred.promise;
- },
- queryItem: function() {
- var deferred, cfg = {};
- // Get details about the specified web map. If the web map is not shared publicly users will
- // be prompted to log-in by the Identity Manager.
- deferred = new Deferred();
- // If we want to get the webmap
- if (this.templateConfig.queryForWebmap) {
- // Use local webmap instead of portal webmap
- if (this.templateConfig.useLocalWebmap) {
- // get webmap js file
- require([this.templateConfig.localWebmapFile], lang.hitch(this, function(webmap) {
- // return webmap json
- cfg.itemInfo = webmap;
- this.itemConfig = cfg;
- deferred.resolve(cfg);
- }));
- }
- // no webmap is set and we have organization's info
- else if (!this.config.webmap && this.config.orgInfo) {
- var defaultWebmap = {
- "item": {
- "title": "Default Webmap",
- "type": "Web Map",
- "description": "A webmap with the default basemap and extent.",
- "snippet": "A webmap with the default basemap and extent.",
- "extent": this.config.orgInfo.defaultExtent
- },
- "itemData": {
- "operationalLayers": [],
- "baseMap": this.config.orgInfo.defaultBasemap
- }
- };
- cfg.itemInfo = defaultWebmap;
- this.itemConfig = cfg;
- deferred.resolve(cfg);
- }
- // use webmap from id
- else {
- arcgisUtils.getItem(this.config.webmap).then(lang.hitch(this, function(itemInfo) {
- // Set the itemInfo config option. This can be used when calling createMap instead of the webmap id
- cfg.itemInfo = itemInfo;
- this.itemConfig = cfg;
- deferred.resolve(cfg);
- }), function(error) {
- if (!error) {
- error = new Error("Error retrieving display item.");
- }
- deferred.reject(error);
- });
- }
- } else {
- // we're done. we dont need to get the webmap
- deferred.resolve();
- }
- return deferred.promise;
- },
- queryApplication: function() {
- // Get the application configuration details using the application id. When the response contains
- // itemData.values then we know the app contains configuration information. We'll use these values
- // to overwrite the application defaults.
- var deferred = new Deferred();
- if (this.config.appid) {
- arcgisUtils.getItem(this.config.appid).then(lang.hitch(this, function(response) {
- var cfg = {};
- if (response.item && response.itemData && response.itemData.values) {
- // get app config values - we'll merge them with config later.
- cfg = response.itemData.values;
- // save response
- cfg.appResponse = response;
- }
- // get the extent for the application item. This can be used to override the default web map extent
- if (response.item && response.item.extent) {
- cfg.application_extent = response.item.extent;
- }
- // get any app proxies defined on the application item
- if (response.item && response.item.appProxies) {
- var layerMixins = array.map(response.item.appProxies, function(p) {
- return {
- "url": p.sourceUrl,
- "mixin": {
- "url": p.proxyUrl
- }
- };
- });
- cfg.layerMixins = layerMixins;
- }
- this.appConfig = cfg;
- deferred.resolve(cfg);
- }), function(error) {
- if (!error) {
- error = new Error("Error retrieving application configuration.");
- }
- deferred.reject(error);
- });
- } else {
- deferred.resolve();
- }
- return deferred.promise;
- },
- queryOrganization: function() {
- var deferred = new Deferred();
- if (this.templateConfig.queryForOrg) {
- // Query the ArcGIS.com organization. This is defined by the sharinghost that is specified. For example if you
- // are a member of an org you'll want to set the sharinghost to be http://.arcgis.com. We query
- // the organization by making a self request to the org url which returns details specific to that organization.
- // Examples of the type of information returned are custom roles, units settings, helper services and more.
- // If this fails, the application will continue to function
- esriRequest({
- url: this.config.sharinghost + "/sharing/rest/portals/self",
- content: {
- "f": "json"
- },
- callbackParamName: "callback"
- }).then(lang.hitch(this, function(response) {
- var cfg = {};
- // save organization information
- cfg.orgInfo = response;
- // get units defined by the org or the org user
- cfg.units = "metric";
- if (response.user && response.user.units) { //user defined units
- cfg.units = response.user.units;
- } else if (response.units) { //org level units
- cfg.units = response.units;
- } else if ((response.user && response.user.region && response.user.region === "US") || (response.user && !response.user.region && response.region === "US") || (response.user && !response.user.region && !response.region) || (!response.user && response.ipCntryCode === "US") || (!response.user && !response.ipCntryCode && kernel.locale === "en-us")) {
- // use feet/miles only for the US and if nothing is set for a user
- cfg.units = "english";
- }
- //Get the basemap group for the organization
- var q = this._parseQuery(response.basemapGalleryGroupQuery);
- this.orgConfig.basemapgroup = {
- id: null,
- title: null,
- owner: null
- };
- if (q.id) {
- this.orgConfig.basemapgroup.id = q.id;
- } else if (q.title && q.owner) {
- this.orgConfig.basemapgroup.title = q.title;
- this.orgConfig.basemapgroup.owner = q.owner;
- }
- // Get the helper services (routing, print, locator etc)
- cfg.helperServices = response.helperServices;
- // are any custom roles defined in the organization?
- if (response.user && esriLang.isDefined(response.user.roleId)) {
- if (response.user.privileges) {
- cfg.userPrivileges = response.user.privileges;
- }
- }
- this.orgConfig = cfg;
- deferred.resolve(cfg);
- }), function(error) {
- if (!error) {
- error = new Error("Error retrieving organization information.");
- }
- deferred.reject(error);
- });
- } else {
- deferred.resolve();
+ }
+ // get items from the group
+ this.portal.queryItems(params).then(lang.hitch(this, function (response) {
+ this.groupItemConfig.groupItems = response;
+ deferred.resolve(response);
+ }), function (error) {
+ deferred.reject(error);
+ });
+ } else {
+ error = new Error("Group undefined.");
+ deferred.reject(error);
+ }
+ } else {
+ // just resolve
+ deferred.resolve();
+ }
+ return deferred.promise;
+ },
+ _queryGroupInfo: function () {
+ var deferred = new Deferred(),
+ error, params;
+ // If we want to get the group info
+ if (this.templateConfig.queryForGroupInfo) {
+ if (this.config.group) {
+ // group params
+ params = {
+ q: "id:\"" + this.config.group + "\"",
+ f: "json"
+ };
+ this.portal.queryGroups(params).then(lang.hitch(this, function (response) {
+ this.groupInfoConfig.groupInfo = response;
+ deferred.resolve(response);
+ }), function (error) {
+ deferred.reject(error);
+ });
+ } else {
+ error = new Error("Group undefined.");
+ deferred.reject(error);
+ }
+ } else {
+ // just resolve
+ deferred.resolve();
+ }
+ return deferred.promise;
+ },
+ _queryDisplayItem: function () {
+ var deferred;
+ // Get details about the specified web map. If the web map is not shared publicly users will
+ // be prompted to log-in by the Identity Manager.
+ deferred = new Deferred();
+ // If we want to get the webmap
+ if (this.templateConfig.queryForWebmap) {
+ // if webmap does not exist
+ if (!this.config.webmap) {
+ // use default webmap for boilerplate
+ this.config.webmap = "24e01ef45d40423f95300ad2abc5038a";
+ }
+ arcgisUtils.getItem(this.config.webmap).then(lang.hitch(this, function (itemInfo) {
+ // Set the itemInfo config option. This can be used when calling createMap instead of the webmap id
+ this.displayItemConfig.itemInfo = itemInfo;
+ deferred.resolve(itemInfo);
+ }), function (error) {
+ if (!error) {
+ error = new Error("Error retrieving display item.");
+ }
+ deferred.reject(error);
+ });
+ } else {
+ // we're done. we dont need to get the webmap
+ deferred.resolve();
+ }
+ return deferred.promise;
+ },
+ _queryApplicationConfiguration: function () {
+ // Get the application configuration details using the application id. When the response contains
+ // itemData.values then we know the app contains configuration information. We'll use these values
+ // to overwrite the application defaults.
+ var deferred = new Deferred();
+ if (this.config.appid) {
+ arcgisUtils.getItem(this.config.appid).then(lang.hitch(this, function (response) {
+ if (response.item && response.itemData && response.itemData.values) {
+ // get app config values - we'll merge them with config later.
+ this.appConfig = response.itemData.values;
+ // save response
+ this.appResponse = response;
+ }
+ // get the extent for the application item. This can be used to override the default web map extent
+ if (response.item && response.item.extent) {
+ this.appConfig.application_extent = response.item.extent;
+ }
+ deferred.resolve(response);
+ }), function (error) {
+ if (!error) {
+ error = new Error("Error retrieving application configuration.");
+ }
+ deferred.reject(error);
+ });
+ } else {
+ deferred.resolve();
+ }
+ return deferred.promise;
+ },
+ _queryOrganizationInformation: function () {
+ var deferred = new Deferred();
+ if (this.templateConfig.queryForOrg) {
+ // Query the ArcGIS.com organization. This is defined by the sharinghost that is specified. For example if you
+ // are a member of an org you'll want to set the sharinghost to be http://.arcgis.com. We query
+ // the organization by making a self request to the org url which returns details specific to that organization.
+ // Examples of the type of information returned are custom roles, units settings, helper services and more.
+ // If this fails, the application will continue to function
+ esriRequest({
+ url: this.config.sharinghost + "/sharing/rest/portals/self",
+ content: {
+ "f": "json"
+ },
+ callbackParamName: "callback"
+ }).then(lang.hitch(this, function (response) {
+ // save organization information
+ this.orgConfig.orgInfo = response;
+ // get units defined by the org or the org user
+ this.orgConfig.units = "metric";
+ if (response.user && response.user.units) { //user defined units
+ this.orgConfig.units = response.user.units;
+ } else if (response.units) { //org level units
+ this.orgConfig.units = response.units;
+ } else if ((response.user && response.user.region && response.user.region === "US") || (response.user && !response.user.region && response.region === "US") || (response.user && !response.user.region && !response.region) || (!response.user && response.ipCntryCode === "US") || (!response.user && !response.ipCntryCode && kernel.locale === "en-us")) {
+ // use feet/miles only for the US and if nothing is set for a user
+ this.orgConfig.units = "english";
+ }
+
+ //Get the basemap group for the organization
+ var q = this._parseQuery(response.basemapGalleryGroupQuery);
+ this.orgConfig.basemapgroup = {
+ id: null,
+ title: null,
+ owner: null
+ };
+ if (q.id) {
+ this.orgConfig.basemapgroup.id = q.id;
+ } else if (q.title && q.owner) {
+ this.orgConfig.basemapgroup.title = q.title;
+ this.orgConfig.basemapgroup.owner = q.owner;
+ }
+
+
+ // Get the helper services (routing, print, locator etc)
+ this.orgConfig.helperServices = response.helperServices;
+ // are any custom roles defined in the organization?
+ if (response.user && esriLang.isDefined(response.user.roleId)) {
+ if (response.user.privileges) {
+ this.orgConfig.userPrivileges = response.user.privileges;
}
- return deferred.promise;
- },
- _parseQuery: function (queryString) {
+ }
+ deferred.resolve(response);
+ }), function (error) {
+ if (!error) {
+ error = new Error("Error retrieving organization information.");
+ }
+ deferred.reject(error);
+ });
+ } else {
+ deferred.resolve();
+ }
+ return deferred.promise;
+ },
+ _parseQuery: function (queryString) {
- var regex = /(AND|OR)?\W*([a-z]+):/ig,
- fields = {},
- fieldName, fieldIndex, result = regex.exec(queryString);
- while (result) {
- fieldName = result && result[2];
- fieldIndex = result ? (result.index + result[0].length) : -1;
+ var regex = /(AND|OR)?\W*([a-z]+):/ig,
+ fields = {},
+ fieldName, fieldIndex, result = regex.exec(queryString);
+ while (result) {
+ fieldName = result && result[2];
+ fieldIndex = result ? (result.index + result[0].length) : -1;
- result = regex.exec(queryString);
+ result = regex.exec(queryString);
- fields[fieldName] = queryString.substring(fieldIndex, result ? result.index : queryString.length).replace(/^\s+|\s+$/g, "").replace(/\"/g, ""); //remove extra quotes in title
- }
- return fields;
+ fields[fieldName] = queryString.substring(fieldIndex, result ? result.index : queryString.length).replace(/^\s+|\s+$/g, "").replace(/\"/g, ""); //remove extra quotes in title
}
- });
+ return fields;
+ }
+ });
});
diff --git a/js/toolbar.js b/js/toolbar.js
index b129a322..c5d92d47 100644
--- a/js/toolbar.js
+++ b/js/toolbar.js
@@ -1,16 +1,19 @@
-define(["dojo/Evented", "dojo/_base/declare", "dojo/_base/window", "dojo/_base/fx", "dojo/_base/html", "dojo/_base/lang", "dojo/has", "dojo/dom", "dojo/dom-class", "dojo/dom-style", "dojo/dom-attr", "dojo/dom-construct", "dojo/dom-geometry", "dojo/on", "dojo/mouse", "dojo/query", "dojo/Deferred"], function (
-Evented, declare, win, fx, html, lang, has, dom, domClass, domStyle, domAttr, domConstruct, domGeometry, on, mouse, query, Deferred) {
+define([
+ "dojo/Evented", "dojo/_base/declare", "dojo/_base/window", "dojo/_base/fx",
+ "dojo/_base/html", "dojo/_base/lang", "dojo/has", "dojo/dom",
+ "dojo/dom-class", "dojo/dom-style", "dojo/dom-attr", "dojo/dom-construct", "dojo/dom-geometry",
+ "dojo/on", "dojo/mouse", "dojo/query", "dojo/Deferred"], function (
+Evented, declare, win, fx, html, lang, has, dom,
+domClass, domStyle, domAttr, domConstruct, domGeometry,
+on, mouse, query, Deferred) {
return declare([Evented], {
-
map: null,
tools: [],
toollist: [],
- snap: true,
- curTool: 0,
+ curTool: -1,
scrollTimer: null,
config: {},
pTools: null,
- pMenu: null,
pPages: null,
constructor: function (config) {
@@ -19,12 +22,14 @@ Evented, declare, win, fx, html, lang, has, dom, domClass, domStyle, domAttr, do
startup: function () {
var deferred = this._init();
- deferred.then(lang.hitch(this, function (config) {
- // optional ready event to listen to
- this.emit("ready", config);
- }), lang.hitch(this, function (error) {
- // optional error event to listen to
- this.emit("error", error);
+ deferred.then(
+ lang.hitch(this, function (config) {
+ // optional ready event to listen to
+ this.emit("ready", config);
+ }),
+ lang.hitch(this, function (error) {
+ // optional error event to listen to
+ this.emit("error", error);
}));
return deferred;
},
@@ -37,14 +42,13 @@ Evented, declare, win, fx, html, lang, has, dom, domClass, domStyle, domAttr, do
on(window, "scroll", lang.hitch(this, this._windowScrolled));
on(window, "resize", lang.hitch(this, this._windowScrolled));
this.pTools = dom.byId("panelTools");
- this.pMenu = dom.byId("panelMenu");
- on(this.pMenu, "click", lang.hitch(this, this._menuClick));
+
this.pPages = dom.byId("panelPages");
//Prevent body scroll when scrolling to the end of the panel content
on(this.pPages, mouse.enter, lang.hitch(this, function () {
if (this._hasScrollbar()) {
- var p = dom.byId("panelContent");
+ var p = dom.byId("panelPages");
if (p) {
domClass.add(p, "modal-scrollbar");
}
@@ -54,7 +58,7 @@ Evented, declare, win, fx, html, lang, has, dom, domClass, domStyle, domAttr, do
}));
on(this.pPages, mouse.leave, lang.hitch(this, function () {
if (this._hasScrollbar === false) {
- var p = dom.byId("panelContent");
+ var p = dom.byId("panelPages");
if (p) {
domClass.remove(p, "modal-scrollbar");
}
@@ -63,22 +67,14 @@ Evented, declare, win, fx, html, lang, has, dom, domClass, domStyle, domAttr, do
}));
- domConstruct.empty(this.pPages);
- // add blank page
- domConstruct.create("div", {
- className: "pageblank",
- id: "page_blank"
- }, this.pPages);
-
deferred.resolve();
return deferred.promise;
},
+
_hasScrollbar: function () {
// The Modern solution
- if (typeof window.innerWidth === "number") {
- return window.innerWidth > document.documentElement.clientWidth;
- }
+ if (typeof window.innerWidth === 'number') return window.innerWidth > document.documentElement.clientWidth;
// rootElem for quirksmode
var rootElem = document.documentElement || document.body;
@@ -86,288 +82,175 @@ Evented, declare, win, fx, html, lang, has, dom, domClass, domStyle, domAttr, do
// Check overflow style property on body for fauxscrollbars
var overflowStyle;
- if (typeof rootElem.currentStyle !== "undefined") {
- overflowStyle = rootElem.currentStyle.overflow;
- }
+ if (typeof rootElem.currentStyle !== 'undefined') overflowStyle = rootElem.currentStyle.overflow;
- overflowStyle = overflowStyle || window.getComputedStyle(rootElem, "").overflow;
+ overflowStyle = overflowStyle || window.getComputedStyle(rootElem, '').overflow;
// Also need to check the Y axis overflow
var overflowYStyle;
- if (typeof rootElem.currentStyle !== "undefined") {
- overflowYStyle = rootElem.currentStyle.overflowY;
- }
+ if (typeof rootElem.currentStyle !== 'undefined') overflowYStyle = rootElem.currentStyle.overflowY;
- overflowYStyle = overflowYStyle || window.getComputedStyle(rootElem, "").overflowY;
+ overflowYStyle = overflowYStyle || window.getComputedStyle(rootElem, '').overflowY;
var contentOverflows = rootElem.scrollHeight > rootElem.clientHeight;
var overflowShown = /^(visible|auto)$/.test(overflowStyle) || /^(visible|auto)$/.test(overflowYStyle);
- var alwaysShowScroll = overflowStyle === "scroll" || overflowYStyle === "scroll";
+ var alwaysShowScroll = overflowStyle === 'scroll' || overflowYStyle === 'scroll';
return (contentOverflows && overflowShown) || (alwaysShowScroll);
},
+
//Create a tool and return the div where you can place content
- createTool: function (tool, panelClass) {
+ createTool: function (tool, panelClass, loaderImg, badgeEvName) {
var name = tool.name;
// add tool
- var pTool = domConstruct.create("div", {
+ var refNode = this.pTools;
+ var tip = this.config.i18n.tooltips[name] || name;
+ var panelTool = domConstruct.create("div", {
className: "panelTool",
- role: "button",
- tabindex: "0",
- id: "panelTool_" + name
- }, this.pTools);
-
- if (!has("touch")) {
- //add a tooltip
- var tip = this.config.i18n.tooltips[name] || name;
- domAttr.set(pTool, "data-title", tip);
+ tabindex: -1,
+ id: "toolButton_" + name,
+ autofocus: true,
+ // "aria-label": tip,
+ }, refNode);
+ var pTool = domConstruct.create("input", {
+ type: "image",
+ src: "images/icons_" + this.config.icons + "/" + name + ".png",
+ title: tip,
+ alt: tip
+ }, panelTool);
+
+ if (!has("touch"))
+ {
domAttr.set(pTool, "title", tip);
- on(pTool, mouse.enter, function () {
- domAttr.set(pTool, "title", "");
- });
- on(pTool, mouse.leave, function () {
- domAttr.set(pTool, "title", tip);
- });
+ }
+
+ if(badgeEvName && badgeEvName !== '') {
+ var setIndicator = domConstruct.create("img", {
+ src:"images/"+badgeEvName+".png",
+ class:"setIndicator",
+ style:"display:none;",
+ tabindex:0,
+ id: 'badge_'+badgeEvName,
+ alt:""
+ });
+ domConstruct.place(setIndicator, panelTool);
}
- domConstruct.create("img", {
- className: "tool",
- src: "images/icons_" + this.config.icons + "/" + name + ".png"
- }, pTool);
on(pTool, "click", lang.hitch(this, this._toolClick, name));
this.tools.push(name);
-
-
// add page
var page = domConstruct.create("div", {
- className: "page",
- id: "page_" + name
+ className: "page hideAttr",
+ id: "page_" + name,
+ // tabindex: 0
}, this.pPages);
var pageContent = domConstruct.create("div", {
- className: "pageContent rounded shadow",
- id: "pageContent_" + name
+ className: "pageContent",
+ id: "pageContent_" + name,
+ role: "dialog",
+ "aria-labelledby": "pagetitle_" + name,
}, page);
- domClass.add(pageContent, panelClass);
-
var pageHeader = domConstruct.create("div", {
id: "pageHeader_" + name,
- className: "pageHeader bg roundedTop"
- }, pageContent);
-
+ className: "pageHeader fr bg",
+ //tabindex: 0,
+ },
+ pageContent);
- domConstruct.create("div", {
+ domConstruct.create("h2", {
className: "pageTitle fc",
- innerHTML: this.config.i18n.tooltips[name] || name
+ innerHTML: this.config.i18n.tooltips[name] || name,
+ //style: 'display:inline',
+ id: "pagetitle_" + name
}, pageHeader);
- domConstruct.create("div", {
- className: "pageHeaderImg",
- innerHTML: " "
- }, pageHeader);
+ if(loaderImg && loaderImg !=="") {
+ domConstruct.create('img',{
+ src: 'images/reload1.gif',
+ alt: 'Reloading',
+ title: 'Reloading'
+ }, domConstruct.create("div", {
+ id: "loading_" + name,
+ class: 'hideLoading small-loading'
+ }, pageHeader));
+ }
+ // domConstruct.create("div", {
+ // className: "pageHeaderImg",
+ // innerHTML: " "
+ // }, pageHeader);
var pageBody = domConstruct.create("div", {
className: "pageBody",
- id: "pageBody_" + name
- }, pageContent);
- return pageBody;
+ tabindex: 0,
+ id: "pageBody_" + name,
+ },
+ pageContent);
+ domClass.add(pageBody, panelClass);
+
+ on(this, "updateTool_" + name, lang.hitch(this, function(name) {
+ pageBody.focus();
+ }));
+ return pageBody;
},
- updatePageNavigation: function () {
- //Adds the up/down and close tools to the page header.
- for (var i = 0; i < this.tools.length; i++) {
- var name = this.tools[i];
- var pageClose = domConstruct.create("div", {
- className: "pageNav pageClose",
- tabindex: "0",
- title: this.config.i18n.nav.close
- }, "pageHeader_" + name);
- if(this.config.icons === "black"){
- domClass.add(pageClose, "icons-dark");
- }
- on(pageClose, "click, keypress", lang.hitch(this, this.closePage));
-
- var pageUp = domConstruct.create("div", {
- className: "pageNav pageUp",
- tabindex: "0",
- title: this.config.i18n.nav.previous
- }, "pageHeader_" + name);
- if(this.config.icons === "black"){
- domClass.add(pageUp, "icons-dark");
- }
- on(pageUp, "click, keypress", lang.hitch(this, this._showPreviousPage, name));
-
- if (name != this.tools[this.tools.length - 1]) {
- var pageDown = domConstruct.create("div", {
- className: "pageNav pageDown",
- tabindex: "0",
- title: this.config.i18n.nav.next
- }, "pageHeader_" + name);
- if(this.config.icons === "black"){
- domClass.add(pageDown, "icons-dark");
- }
- on(pageDown, "click, keypress", lang.hitch(this, this._showNextPage, name));
- }
-
+ _toolClick: function (name) {
+
+ var defaultBtns = dojo.query(".panelToolDefault");
+ var defaultBtn;
+ if(defaultBtns !== undefined && defaultBtns.length > 0) {
+ defaultBtn = defaultBtns[0].id.split("_")[1];
}
-
- },
- setContent: function (name, content) {
- domConstruct.place(content, "pageBody_" + name, "last");
- },
-
- activateTool: function (name) {
- //Instead of scrolling to the tool just go there.
- var num = this._getPageNum(name) + 1;
- var box = html.getContentBox(dom.byId("panelContent"));
-
- var endPos = num * box.h;
-
- document.body.scrollTop = endPos;
- document.documentElement.scrollTop = endPos;
-
- this._updateMap();
-
-
- this.curTool = num;
- this._updateTool(num);
- },
-
- _toolClick: function (name) {
- this._showPage(name);
- },
-
- _getPageNum: function (name) {
- for (var i = 0; i < this.tools.length; i++) {
- if (this.tools[i] == name) {
- return i;
+ this._updateMap(); // ! out of place
+ var active = false;
+ var page = dom.byId("page_"+name);
+ var hidden = page.classList.contains("hideAttr");
+ var pages = query(".page");
+ pages.forEach(function(p){
+ if(hidden && p === page) {
+ active = true;
}
- }
- return 0;
- },
- _showPage: function (name) {
- var num = this._getPageNum(name) + 1;
-
- if (num != this.curTool) {
- this._scrollToPage(num);
- } else {
- this._scrollToPage(0);
- }
- },
- _showPreviousPage: function (name) {
- var num = this._getPageNum(name);
- this._scrollToPage(num);
-
- },
-
- _showNextPage: function (name) {
- var num = this._getPageNum(name) + 2;
- this._scrollToPage(num);
- },
-
- closePage: function (e) {
- this._scrollToPage(-1);
- },
- _scrollToPage: function (num) {
-
- var box = html.getContentBox(dom.byId("panelContent"));
-
- var startPos = this.curTool * box.h;
- var endPos = num * box.h;
- var diff = Math.abs(num - this.curTool);
- this.snap = false;
- if (diff == 1) {
- this._animateScroll(startPos, endPos);
- } else {
- document.body.scrollTop = endPos;
- document.documentElement.scrollTop = endPos;
- this._updateMap();
- this.snap = true;
- }
- this.curTool = num;
- this._updateTool(num);
-
- },
-
- // window scrolled
- _windowScrolled: function (evt) {
-
- if (this.scrollTimer) {
- clearTimeout(this.scrollTimer);
- }
- if (this.snap === true) {
- this.scrollTimer = setTimeout(lang.hitch(this, this._snapScroll), 300);
- }
- },
- _snapScroll: function () {
-
- var startPos = domGeometry.docScroll().y;
- var box = html.getContentBox(dom.byId("panelContent"));
- var numActual = startPos / box.h;
- var num = Math.round(numActual);
+ });
- if (numActual > this.curTool) {
- if (numActual - this.curTool > 0.2) {
- num = Math.ceil(startPos / box.h);
+ pages.forEach(function(p){
+ if(hidden && p === page) {
+ domClass.replace(p, "showAttr","hideAttr");
+ } else {
+ domClass.replace(p,"hideAttr","showAttr");
}
- if (num > this.tools.length - 1) {
- num = this.tools.length - 1;
- }
- } else if (numActual < this.curPage) {
- if (this.curTool - numActual > 0.2) {
- num = Math.floor(startPos / box.h);
- }
- if (num < 0) {
- num = 0;
+ });
+ var tool = dom.byId("toolButton_"+name);
+ var tools = query(".panelTool");
+ this.emit("updateTool", name);
+ tools.forEach(lang.hitch(this, function(t){
+ if(active && t === tool) {
+ domClass.add(t, "panelToolActive");
+ this.emit("updateTool_"+name);
+ } else {
+ domClass.remove(t,"panelToolActive");
}
- }
- var endPos = num * box.h;
+ }));
- this.curTool = num;
- this._updateTool(num);
-
- if (num != numActual) {
- this._animateScroll(startPos, endPos);
+ if(!active && defaultBtns !== undefined) {
+ this._activateDefautTool();
}
-
},
- _animateScroll: function (start, end) {
- //var me = this;
- var anim = new fx.Animation({
- duration: 500,
- curve: [start, end]
- });
- on(anim, "Animate", function (v) {
- document.body.scrollTop = v;
- document.documentElement.scrollTop = v;
- });
-
- on(anim, "End", lang.hitch(this, function () {
- setTimeout(lang.hitch(this, this._resetSnap), 500);
- this._updateMap();
+ _atachEnterKey: function(onButton, clickButton) {
+ on(onButton, 'keydown', lang.hitch(clickButton, function(event){
+ if(event.keyCode=='13')
+ this.click();
}));
-
- anim.play();
},
- // highlight the active tool on the toolbar
- _updateTool: function (num) {
- query(".panelTool").removeClass("panelToolActive");
- var name = this.tools[num - 1];
- if (name) {
- domClass.add("panelTool_" + name, "panelToolActive");
- }
- this.emit("updateTool", name);
- },
_updateMap: function () {
if (this.map) {
this.map.resize();
@@ -375,21 +258,32 @@ Evented, declare, win, fx, html, lang, has, dom, domClass, domStyle, domAttr, do
}
},
- _resetSnap: function () {
- this.snap = true;
-
- },
-
- // menu click
- _menuClick: function () {
- if (query("#panelTools").style("display") == "block") {
- query("#panelTools").style("display", "none");
- this.closePage();
-
- } else {
- query("#panelTools").style("display", "block");
+ _activateDefautTool: function() {
+ var defaultBtns = dojo.query(".panelToolDefault");
+ var defaultBtn;
+ if(defaultBtns !== undefined && defaultBtns.length>0) {
+ defaultBtn = defaultBtns[0].id.split("_")[1];
}
- this._updateMap();
- }
+ if(defaultBtn !== undefined) {
+ this._toolClick(defaultBtn);
+ }
+ else if (this.config.activeTool !== "" && has(this.config.activeTool)) {
+ toolbar.activateTool(this.config.activeTool);
+ }
+ // else {
+ // toolbar._closePage();
+ // }
+ },
+
+ // // menu click
+ // _menuClick: function () {
+ // if (query("#panelTools").style("display") == "block") {
+ // query("#panelTools").style("display", "none");
+ // this._closePage();
+ // } else {
+ // query("#panelTools").style("display", "block");
+ // }
+ // this._updateMap();
+ // }
});
-});
\ No newline at end of file
+});
diff --git a/js/utils.js b/js/utils.js
new file mode 100644
index 00000000..b4432769
--- /dev/null
+++ b/js/utils.js
@@ -0,0 +1,139 @@
+"use strict"
+
+Number.prototype.padLeft = function (n,str){
+ return new Array(n-String(this).length+1).join(str||'0')+this;
+};
+
+Date.prototype.getSQLDate = function() {
+ if(this.toDateString() === "Invalid Date") {
+ return null;
+ }
+ return this.getFullYear().padLeft(4)+(this.getMonth()+1).padLeft(2)+this.getDate().padLeft(2);
+};
+
+
+// Add ECMA262-5 method binding if not supported natively
+//
+if (!('bind' in Function.prototype)) {
+ Function.prototype.bind= function(owner) {
+ var that= this;
+ if (arguments.length<=1) {
+ return function() {
+ return that.apply(owner, arguments);
+ };
+ } else {
+ var args= Array.prototype.slice.call(arguments, 1);
+ return function() {
+ return that.apply(owner, arguments.length===0? args : args.concat(Array.prototype.slice.call(arguments)));
+ };
+ }
+ };
+}
+
+// Add ECMA262-5 string trim if not supported natively
+//
+if (!('trim' in String.prototype)) {
+ String.prototype.trim= function() {
+ return this.replace(/^\s+/, '').replace(/\s+$/, '');
+ };
+}
+
+// if (!Array.prototype.remove) {
+// Array.prototype.remove = function() {
+// var what, a = arguments, L = a.length, ax;
+// while (L && this.length) {
+// what = a[--L];
+// while ((ax = this.indexOf(what)) !== -1) {
+// this.splice(ax, 1);
+// }
+// }
+// return this;
+// };
+// }
+// Add ECMA262-5 Array methods if not supported natively
+//
+if (!Array.prototype.find) {
+ Array.prototype.find = function(predicate) {
+ if (this === null) {
+ throw new TypeError('Array.prototype.find called on null or undefined');
+ }
+ if (typeof predicate !== 'function') {
+ throw new TypeError('predicate must be a function');
+ }
+ var list = Object(this);
+ var length = list.length >>> 0;
+ var thisArg = arguments[1];
+ var value;
+
+ for (var i = 0; i < length; i++) {
+ value = list[i];
+ if (predicate.call(thisArg, value, i, list)) {
+ return value;
+ }
+ }
+ return undefined;
+ };
+}
+if (!('indexOf' in Array.prototype)) {
+ Array.prototype.indexOf= function(find, i /*opt*/) {
+ if (i===undefined) i= 0;
+ if (i<0) i+= this.length;
+ if (i<0) i= 0;
+ for (var n= this.length; ithis.length-1) i= this.length-1;
+ for (i++; i-->0;) /* i++ because from-argument is sadly inclusive */
+ if (i in this && this[i]===find)
+ return i;
+ return -1;
+ };
+}
+if (!('forEach' in Array.prototype)) {
+ Array.prototype.forEach= function(action, that /*opt*/) {
+ for (var i= 0, n= this.length; iApp Settings",
+ "category":"Configure template ",
"fields":[
- {
- "type": "appproxies"
+ { "type":"webmap"},
+
+ { "type":"string",
+ "stringFieldOption": "richtext",
+ "label": "Alternate Map Text ",
+ "tooltip": "Define text that will be read by screen reader",
+ "fieldName":"altMapText"
},
- {
- "type":"webmap"
+ { "type": "paragraph",
+ "value": "The primary purpose of alternative map text is to be read by screen readers to allow the content and function of the map to be accessible to users with visual or certain cognitive disabilities."
},
- {
+
+ { "label":"Description ",
+ "type":"string",
+ "fieldName":"description",
+ "placeHolder":"Defaults to web map description.",
+ "stringFieldOption":"richtext"},
+ { "type": "paragraph",
+ "value": "When present, this markup will replace the map description in the Details panel."
+ },
+ { "label":"Title: ",
"placeHolder":"Defaults to web map title",
- "label":"Title:",
"fieldName":"title",
"type":"string",
- "tooltip":"Defaults to web map title"
- },
- {
- "placeHolder":"Optional subtitle text",
- "label":"SubTitle:",
- "fieldName":"subtitle",
- "type":"string",
- "tooltip":"Optional subtitle text"
- },
- {
- "label":"Title logo:",
+ "tooltip":"Defaults to web map title" },
+ { "label":"Logo Image: ",
"fieldName":"logo",
"type":"string",
- "tooltip":"Defaults to sample logo"
- },
- {
+ "tooltip":"Defaults to sample logo"},
+ { "label":"Logo Alternate Text: ",
+ "fieldName":"logoAltText",
"type":"string",
- "fieldName":"description",
- "label":"Details",
- "placeHolder":"Defaults to web map description.",
- "tooltip":"Enter content for the details panel",
- "stringFieldOption":"richtext"
+ "tooltip":"Type here the text from the Logo Image"},
+ { "label":"Animated Marker ",
+ "type":"boolean",
+ "fieldName":"animated_marker"},
+ { "label":"Animated Marker File: ",
+ "fieldName":"marker",
+ "type":"string",
+ "tooltip":"Defaults to blue-animated"},
+ { "label":"Marker size: ",
+ "fieldName":"marker_size",
+ "type":"int",
+ "tooltip":"Size of the Marker"},
+
+ { "label":"Access Keys ",
+ "fieldName":"alt_keys",
+ "type":"boolean",
+ "tooltip":"Show hints for alternate keys when pressing ALT key."},
+ { "type": "paragraph",
+ "value": "The Access Key is a shortcut to activate or focus a screen control. The way of accessing the shortcut key is varying in different browsers. Most browsers use the [Alt]+# or [Alt][Shift]+#. However the shortcut can be set to another combination of keys."
},
- {
+
+
+ { "label":"New Icons ",
+ "type":"boolean",
+ "fieldName":"new_icons"}
+ ]
+ },
+ {
+ "category":"Colors ",
+ "fields":[
+ { "label":"Theme Color:",
"type":"color",
"fieldName":"theme",
- "tooltip":"Color theme to use",
- "label":"Color Theme:"
- },
- {
+ "tooltip":"Title bar color"},
+ { "label":"Title Color:",
"type":"color",
"fieldName":"color",
- "tooltip":"Title bar text color",
- "label":"Title Color:"
- },
- {
+ "tooltip":"Title bar text color"},
+ { "label":"Hover Color:",
+ "type":"color",
+ "fieldName":"hoverColor",
+ "tooltip":"Hover over color"},
+ { "label":"Focus Color:",
+ "type":"color",
+ "fieldName":"focusColor",
+ "tooltip":"Focus border color"},
+ { "label":"Active Color:",
+ "type":"color",
+ "fieldName":"activeColor",
+ "tooltip":"Selection color"},
+ { "label":"Icon color:",
"type":"string",
"fieldName":"icons",
"tooltip":"Icon color",
- "label":"Icon color:",
"options":[
{
"label":"White",
@@ -63,49 +98,16 @@
"label":"Black",
"value":"black"
}
- ]
- },{
- "type":"paragraph",
- "value": "Use the Custom css option to paste css that overwrites rules in the app."
- },{
- "type":"string",
- "fieldName": "customstyle",
- "tooltip":"Custom css",
- "label": "Custom css"
- },{
- "type": "boolean",
- "fieldName": "popupPanel",
- "label": "Display popup content in floating panel"
- }
+ ]}
]
- },{
- "category":"Splash Screen",
- "fields":[{
- "type": "boolean",
- "fieldName": "splashModal",
- "tooltip": "Enable Splash Screen",
- "label": "Splash Screen"
- },{
- "type": "string",
- "fieldName": "splashTitle",
- "label": "Splash screen title",
- "tooltip": "Define splash screen title"
- },{
- "type":"string",
- "fieldName":"splashContent",
- "label":"Splash screen content text",
- "tooltip":"Define splash screen content",
- "stringFieldOption":"richtext"
- } ]
- },
+ },
{
"category":"Tools",
"fields":[
- {
+ { "label":"Active Tool:",
"type":"string",
"fieldName":"activeTool",
"tooltip":"Active Tool",
- "label":"Active Tool:",
"options":[
{
"label":"None",
@@ -123,6 +125,10 @@
"label":"Details",
"value":"details"
},
+ {
+ "label":"Instructions",
+ "value":"instructions"
+ },
{
"label":"Edit",
"value":"edit"
@@ -131,6 +137,14 @@
"label":"Layers",
"value":"layers"
},
+ {
+ "label":"Features",
+ "value":"features"
+ },
+ {
+ "label":"Filters",
+ "value":"filter"
+ },
{
"label":"Legend",
"value":"legend"
@@ -151,95 +165,103 @@
"label":"Share",
"value":"share"
}
- ]
- },
- {
+ ]},
+
+ { "label":"Details",
"type":"boolean",
- "fieldName":"tool_basemap",
- "label":"Basemap Gallery"
- },
- {
+ "fieldName":"tool_details"},
+ { "label":"Instructions",
"type":"boolean",
- "fieldName":"tool_bookmarks",
- "label":"Bookmarks"
- },
- {
+ "fieldName":"tool_instructions"},
+ { "label":"Overview Map",
"type":"boolean",
- "fieldName":"tool_locate",
- "label":"Find Location"
- },{
- "type": "boolean",
- "fieldName": "locate_track",
- "label": "Enable tracking"
- },
- {
+ "fieldName":"tool_overview"},
+ { "label":"Basemap Gallery",
"type":"boolean",
- "fieldName":"tool_home",
- "label":"Home Extent Button"
- },
- {
+ "fieldName":"tool_basemap"},
+ { "label":"Bookmarks",
"type":"boolean",
- "fieldName":"scalebar",
- "label":"Scalebar"
- },
- {
+ "fieldName":"tool_bookmarks"},
+ { "label":"Find Location",
"type":"boolean",
- "fieldName":"tool_layers",
- "label":"Layer List"
- },{
+ "fieldName":"tool_locate"},
+ { "label":"Home Button",
"type":"boolean",
- "fieldName": "tool_sublayers",
- "label": "Include sublayers in Layer List"
- },{
- "type": "boolean",
- "fieldName": "tool_layerlegend",
- "label": "Include legend in Layer List"
- },{
- "type": "boolean",
- "fieldName": "tool_opacity",
- "label": "Include opacity slider in Layer List"
- },
- {
+ "tooltip":"(Default Extent)",
+ "fieldName":"tool_home"},
+ { "label":"Legend",
"type":"boolean",
- "fieldName":"tool_legend",
- "label":"Legend"
- },
- {
+ "fieldName":"tool_legend"},
+ { "label":"Layers",
"type":"boolean",
- "fieldName":"tool_details",
- "label":"Map Details"
- },
- {
+ "fieldName":"tool_layers"},
+ { "label":"Feature List",
"type":"boolean",
- "fieldName":"tool_measure",
- "label":"Measure Tool"
- },
- {
+ "fieldName":"tool_features"},
+ { "label":"Filters",
"type":"boolean",
- "fieldName":"tool_overview",
- "label":"Overview Map"
- },
- {
+ "fieldName":"tool_filter"},
+ { "label":"Measure Tool",
"type":"boolean",
- "fieldName":"tool_share",
- "label":"Share Tools"
- }
+ "fieldName":"tool_measure"},
+ { "label":"Share Tools",
+ "type":"boolean",
+ "fieldName":"tool_share"},
+ { "label":"Print Button",
+ "type":"boolean",
+ "fieldName":"tool_print"},
+ { "label":"Scalebar",
+ "type":"boolean",
+ "fieldName":"scalebar"},
+ { "label":"Extended Navigation Tool Bar",
+ "type":"boolean",
+ "fieldName":"navigation"}
]
- },{
+ },
+ {
"category": "Search Settings",
"fields": [
{
- "type":"paragraph",
- "value": "Enable search to allow users to find a location or data in the map. Configure the search settings to refine the experience in your app by setting the default search resource, placeholder text, etc."
+ "type": "paragraph",
+ "value": "Enable/disable the search tool and optionally select layers (and fields) to add to the search tool."
},
{
+ "label":"Select search layers and fields",
+ "fieldName":"searchLayers",
+ "type":"multilayerandfieldselector",
+ "tooltip":"Select layer and fields to search",
+ "layerOptions":{
+ "supportedTypes":[
+ "FeatureLayer"
+ ],
+ "geometryTypes":[
+ "esriGeometryPoint",
+ "esriGeometryLine",
+ "esriGeometryPolyline",
+ "esriGeometryPolygon"
+ ]
+ },
+ "fieldOptions":{
+ "supportedTypes":[
+ "esriFieldTypeString"
+ ]
+ }
+ },{
"type":"boolean",
"fieldName":"tool_search",
- "label":"Enable search tool"
+ "label":"Address Finder"
+ },
+ {
+ "type":"boolean",
+ "fieldName":"searchExtent",
+ "label":"Prioritize search results in current extent."
+ },{
+ "type":"paragraph",
+ "value": "When Location Search is true the search widget will allow users to search for addresses and locations using one or more locators and also search the layers and fields specified in the Search Layers configuration option. Unchecking the Location Search option will remove the locator search and only configured search layers will be displayed."
},{
- "type":"search",
- "fieldName": "searchConfig",
- "label": "Configure Search"
+ "type": "boolean",
+ "fieldName": "locationSearch",
+ "label": "Location Search"
}
]
},
@@ -296,75 +318,170 @@
"label":"Add Legend to Output"
}
]
- },{
- "category": "Custom URL Parameter",
- "fields": [
- {
- "type": "paragraph",
- "value": "Setup the app to support a custom url parameter. For example if your map contains a feature layer with parcel information and you'd like to be able to find parcels using a url parameter you can use this section to do so. Select a layer and search field then define the name of a custom param. Once you've defined these values you can append the custom search to your application url using the custom parameter name you define. For example, if I set the custom param value to parcels a custom url would look like this index.html?parcel=3045"
- },{
- "placeHolder":"i.e. parcels",
- "label":"URL param name:",
- "fieldName":"customUrlParam",
+ },
+ {
+ "category":"Languages",
+ "fields":[
+ { "label":"Control with label",
+ "type":"boolean",
+ "fieldName":"languageLabel",
+ "tooltip": "Place a localized label in front of the Language control."},
+ {
+ "type":"paragraph",
+ "value":"Language 1 "
+ },
+
+ { "label": "Language code",
+ "fieldName":"lang1code",
+ "type":"string"
+ },
+ { "type":"paragraph",
+ "value":"Enter the locale of the language. Example: 'en-us'"
+ },
+ { "label": "Language Short Name",
+ "fieldName":"lang1shortName",
+ "type":"string"
+ },
+ { "type": "paragraph",
+ "value":"The name that will appear on the Language widget as active language. Leave it blank to display first two letters of language code when no image. You may use national charactes here to change the default display."
+ },
+ { "label": "Flag Image",
+ "fieldName":"lang1imageSrc",
+ "type":"string"
+ },
+ { "type": "paragraph",
+ "value":"The location of the image representing the flag of the country. Note: Leave it blank to display no image and show the Language Short Name instead."
+ },
+ { "label": "Language name",
+ "fieldName":"lang1name",
+ "type":"string"
+ },
+ { "type":"paragraph",
+ "value":"The name that will appear in the combo-box pull-down."
+ },
+ { "label": "Application Id",
+ "fieldName":"lang1appId",
+ "type":"string"
+ },
+ { "type":"paragraph",
+ "value":"ID of application that will restart for this language. Note: you may want another application to customize layers, data and other custom attributes. Leave blank to use same application."
+ },
+
+ { "type":"paragraph",
+ "value":"Language 2 "
+
+ },
+ { "label": "Language code",
+ "fieldName":"lang2code",
"type":"string",
- "tooltip":"Custom URL param name"
- },{
- "type":"layerAndFieldSelector",
- "fieldName":"customUrlLayer",
- "label":"Layer to search for custom url param value",
- "tooltip":"Url param search layer",
- "fields":[
- {
- "multipleSelection":false,
- "fieldName":"urlField",
- "label":"URL param search field",
- "tooltip":"URL param search field"
- }
- ],
- "layerOptions":{
- "supportedTypes":[
- "FeatureLayer"
- ],
- "geometryTypes":[
- "esriGeometryPoint",
- "esriGeometryLine",
- "esriGeometryPolygon"
- ]
- }
- }
+ "tooltip": "The locale of language 2."
+ },
+ { "label": "Language Short Name",
+ "fieldName":"lang2shortName",
+ "type":"string",
+ "tooltip": "The two-letter name that will appear on the Language widget."
+ },
+ { "label": "Flag Image",
+ "fieldName":"lang2imageSrc",
+ "type":"string",
+ "tooltip": "The location of a 22x22 image."
+ },
+ { "label": "Language name",
+ "fieldName":"lang2name",
+ "type":"string",
+ "tooltip": "The name that will appear in the combo-box pull-down."
+ },
+ { "label": "Application Id",
+ "fieldName":"lang2appId",
+ "type":"string",
+ "tooltip": "Application ID for language 2."
+ },
- ]
+ { "type":"paragraph",
+ "value":"Language 3 "
+ },
+ { "label": "Language code",
+ "fieldName":"lang3code",
+ "type":"string",
+ "tooltip": "The locale of language 3."
+ },
+ { "label": "Language Short Name",
+ "fieldName":"lang3shortName",
+ "type":"string",
+ "tooltip": "The name that will appear on the Language widget."
+ },
+ { "label": "Flag Image",
+ "fieldName":"lang3imageSrc",
+ "type":"string",
+ "tooltip": "The location of a 22x22 image."
+ },
+ { "label": "Language name",
+ "fieldName":"lang3name",
+ "type":"string",
+ "tooltip": "The name that will appear in the combo-box pull-down."
+ },
+ { "label": "Application Id",
+ "fieldName":"lang3appId",
+ "type":"string",
+ "tooltip": "Application ID for language 3."
+ }
+ ]
}
],
"values":{
"icons":"white",
+ "new_icons":false,
+ "animated_marker":true,
+ "marker":"images/ripple-dot1.gif",
+ "marker_size":"35",
+ "alt_keys":true,
"logo":"images/logo.png",
- "color":"#fff",
- "theme":"80ab00",
- "activeTool":"legend",
+ "logoAltText":"",
+
+ "color":"#ffffff",
+ "hoverColor":"#00A9E6",
+ "focusColor":"#FF7700",
+ "activeColor":"#00b9f6",
+ "theme":"#005ce6",
+
+ "activeTool":"details",
"scalebar":false,
- "splashModal": false,
- "tool_print":true,
+ "navigation":false,
"tool_print_layouts":false,
"tool_print_legend":false,
"tool_share":true,
"tool_overview":true,
"tool_measure":true,
"tool_details":true,
+ "tool_instructions":true,
+ "tool_filter":true,
"tool_legend":true,
"tool_layers":true,
- "tool_sublayers": true,
- "tool_opacity": true,
- "tool_layerlegend": true,
"tool_home":true,
"tool_locate":true,
- "locate_track": false,
"tool_edit":true,
"tool_edit_toolbar":false,
"tool_bookmarks":true,
"tool_basemap":true,
"tool_search":true,
+ "tool_print":true,
"locationSearch": true,
- "popupPanel": false
+ "searchExtent":false,
+
+ "languageLabel":true,
+
+ "lang1shortName": "EN",
+ "lang1name": "English",
+ "lang1code": "EN-US",
+ "lang1imageSrc": "images/flag.uk.22.png",
+
+ "lang2shortName": "FR",
+ "lang2name": "French",
+ "lang2code": "FR-CA",
+ "lang2imageSrc": "images/flag.fr.22.png",
+
+ "lang3shortName": "",
+ "lang3name": "",
+ "lang3code": ""
}
}