JS API 3.29 Print/Export map as an image?

4495
10
Jump to solution
08-06-2019 10:48 AM
Claire_Peterson
Occasional Contributor

I have a map that was created using "Selecting Features Using URL Parameters"  where an ID is passed in the URL and the map creates a graphic of the selected feature, zooms to it and hides everything else in the layer (so I can only see the feature that the object ID matches the ID in the URL (along with the basemap and another feature layer). It is a ArcGIS API for JavaScript map built with 3.29 and the map is displayed in a dijit Border Container / Content Pane.

Is there any way to take the final rendered map an convert it into an image to be used elsewhere, say in a PDF along with attributes from that selected feature? The layer that is getting queried is behind credentials so when the page first loads it asks for a log in and then the map renders as it should.

I have tried the screenshot method using html2canvas, canvas.toBlob, Filesaver but the screenshot does not contain anything other than the tiled basemap.

Any help would be greatly appreciated. Thank you.

0 Kudos
1 Solution

Accepted Solutions
BenElan
Esri Contributor

This worked for me

<html>
<head>
  <meta charset="utf-8" />
  <meta name="viewport" content="initial-scale=1, maximum-scale=1, user-scalable=no" />
  <title>MISIN Treatment Tracker: Print</title>
  <link rel="stylesheet" href="https://js.arcgis.com/3.29/dijit/themes/claro/claro.css">
  <link rel="stylesheet" href="https://js.arcgis.com/3.29/esri/css/esri.css">
<!--js scripts to print map-->
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.4.1/jquery.min.js"></script>
<script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/jspdf/1.3.2/jspdf.min.js"></script>
<script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/html2canvas/0.4.1/html2canvas.js"></script>
<script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/javascript-canvas-to-blob/3.15.0/js/canvas-to-blob.js"></script>
<script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/FileSaver.js/1.3.8/FileSaver.js"></script>
<!--end print scripts-->
<style>
@media print {
  #printButton {
    display: none;
  }
}
</style>
<!-- START ESRI MAP SCRIPT -->
<script>var dojoConfig = { parseOnLoad: true }</script>
<script src="https://js.arcgis.com/3.29/"></script>
<script>
var theMap;
var cred = "esri_jsapi_id_manager_data";
var symbol, infoTemplate;
var OID;
require([
  "esri/map",
  "esri/SpatialReference",
  "esri/layers/ArcGISTiledMapServiceLayer",
  "esri/layers/ArcGISDynamicMapServiceLayer",
  "esri/layers/FeatureLayer",
  "esri/layers/ImageParameters",
  "esri/symbols/SimpleMarkerSymbol",
  "esri/symbols/SimpleLineSymbol",
  "esri/symbols/SimpleFillSymbol",
  "esri/layers/LayerDrawingOptions",
  "esri/layers/LabelLayer",
  "esri/layers/LabelClass",
  "esri/symbols/TextSymbol",
  "esri/renderers/SimpleRenderer",
  "esri/graphic",
  "esri/InfoTemplate",
  "esri/urlUtils",
  "esri/arcgis/utils",
  "esri/graphicsUtils",
  "esri/dijit/Legend",
  "esri/dijit/Scalebar",
  "esri/dijit/Print",
  "esri/tasks/query",
  "esri/tasks/QueryTask",
  "esri/tasks/PrintTask",
  "esri/tasks/PrintParameters",
  "esri/tasks/PrintTemplate",
  "esri/request",
  "esri/config",
  "esri/geometry/Extent",
  "esri/IdentityManager",
  "esri/lang",
  "dojo/_base/array",
  "dojo/_base/Color",
  "dojo/_base/unload",
  "dojo/cookie",
  "dojo/json",
  //"dojo/_base/json",
  "dojo/parser",
  "dojo/dom-construct",
  "dojo/dom-class",
  "dojo/dom",
  "dojo/on",
  "dijit/layout/BorderContainer",
  "dijit/layout/ContentPane",
  "dijit/form/Button",
  "dojo/domReady!",
], function(
  Map,
  //MapView,
  SpatialReference,
  ArcGISTiledMapServiceLayer,
  ArcGISDynamicMapServiceLayer,
  FeatureLayer,
  ImageParameters,
  SimpleMarkerSymbol,
  SimpleLineSymbol,
  SimpleFillSymbol,
  LayerDrawingOptions,
  LabelLayer,
  LabelClass,
  TextSymbol,
  SimpleRenderer,
  Graphic,
  InfoTemplate,
  urlUtils,
  arcgisUtils,
  graphicsUtils,
  Legend,
  Scalebar,
  Print,
  Query,
  QueryTask,
  PrintTask,
  PrintParameters,
  PrintTemplate,
  esriRequest,
  esriConfig,
  Extent,
  esriId,
  esriLang,
  arrayUtils,
  Color,
  baseUnload,
  cookie,
  JSON,
  parser,
  domConstruct,
  domClass,
  dom,
  on,
  BorderContainer,
  ContentPane,
  Button
  ){
    function init()
    {
      // store credentials/serverInfos before the page unloads
     baseUnload.addOnUnload(storeCredentials);
     // look for credentials in local storage
     loadCredentials();
     //parser.parse();
     esriConfig.defaults.io.proxyUrl = "/proxy/";
     // START OF ESRI WEBMAP CREATION
    //create the map
    theMap = new Map("mapdiv", {
      basemap:"topo",
      showLabels: true,
      });
      
    //Disable Map Navigation
    theMap.on("load", function() {
    theMap.disableMapNavigation();
    theMap.hideZoomSlider();
  });

    // print dijit
        var printer = new Print({
            map: theMap,
url: "https://utility.arcgisonline.com/arcgis/rest/services/Utilities/PrintingTools/GPServer/Export%20Web%20Map%20Task"
        }, dom.byId("printButton"));
        printer.startup();

    // Create labels for the National Wetlands Inventory Layer
    var labelField = "WETLAND_TYPE"
    var wetlandsColor = new Color ("#0E881B");
    var wetlandsLine = new SimpleLineSymbol("solid", wetlandsColor, 1.5);
    var wetlandsRenderer = new SimpleRenderer(wetlandsLine);
    var wetlandsLabel = new TextSymbol().setColor(wetlandsColor);
    wetlandsLabel.font.setSize("10pt");
    wetlandsLabel.font.setFamily("arial");
    var json = {
      "labelExpressionInfo": {"value": "{WETLAND_TYPE}"}
    };

    //create instance of LabelClass (note: multiple LabelClasses can also be passed in as an array)
    var labelClass = new LabelClass(json);
    labelClass.symbol = wetlandsLabel;

    //Add National Wetlands Inventory
    var wetlands = new FeatureLayer("https://gisago.mcgi.state.mi.us/arcgis/rest/services/OpenData/hydro/MapServer/18");
    wetlands.setRenderer(wetlandsRenderer)
    wetlands.setLabelingInfo([ labelClass ]);
    theMap.addLayer(wetlands);

    //Use the ImageParameters to set map service layer definitions and map service visible layers before adding to the client map.
    var imageParameters = new ImageParameters();

    //only certain layers to be visible. This can only be done with a dynamic map service and it does impact performance. Cached map services are recommended.
    imageParameters.layerIds = [2];
    imageParameters.layerOption = ImageParameters.LAYER_OPTION_SHOW;
    imageParameters.transparent = true;

    //construct ArcGISDynamicMapServiceLayer with imageParameters from above
    var dynamicMapServiceLayer = new ArcGISDynamicMapServiceLayer("https://fuzzy.asets.msu.edu/arcgis/rest/services/MISIN/misin_treatments/MapServer",
    {"opacity": 0.0},
    {"imageParameters": imageParameters});
    theMap.addLayer(dynamicMapServiceLayer);

    //build query task
    var queryTask = new QueryTask("https://fuzzy.asets.msu.edu/arcgis/rest/services/MISIN/misin_treatments/MapServer/2");
    //build query filter
    var query = new Query();
    query.returnGeometry = true;
    query.outFields = ["*"];
    //create symbol for selected features
    symbol = new SimpleFillSymbol(SimpleFillSymbol.STYLE_SOLID,
  new SimpleLineSymbol(SimpleLineSymbol.STYLE_SOLID,
  new dojo.Color([64,124,248]), 2),new dojo.Color([189,209,253]));

    //pass the url parameters.
    var urlObject = urlUtils.urlToObject(window.location.href);
    if (urlObject.query)
    {
      if (urlObject.query.id)
      { OID = urlObject.query.id; }
    //set query based on the parameters
    var treatmentid = "OBJECTID = '" + OID + "'";
    query.where = treatmentid;

    //execute query and call showResults on completion
    //queryTask.execute(query,showResults);
    }
    //Execute task and call showResults on completion
    queryTask.execute(query, showResults);
    }
    function showResults(featureSet)
    {
    //remove all graphics on the maps graphics layer
    theMap.graphics.clear();
    theMap.infoWindow.hide();

    //QueryTask returns a featureSet.  Loop through features in the featureSet and add them to the map.
    //Performance enhancer - assign featureSet array to a single variable.
    var resultFeatures = featureSet.features;
    for (var i=0, il=resultFeatures.length; i<il; i++)
    {
    //Get the current feature from the featureSet. Feature is a graphic
    var graphic = resultFeatures[i];
    graphic.setSymbol(symbol);
    //Set the infoTemplate.
    graphic.setInfoTemplate(infoTemplate);
    //Add graphic to the map graphics layer.
    theMap.graphics.add(graphic);
    }

    //Zoom to the extent of the graphics
    var myFeatureExtent = esri.graphicsExtent(resultFeatures);
    theMap.setExtent(myFeatureExtent.getExtent().expand(3));
    //Refresh the URL with the currently selected parcel
    window.history.pushState(null,null,"?id=" + graphic.attributes.OBJECTID);
    }

    // END OF ESRI MAP CREATION

    // STORE CREDENTIALS
    function loadCredentials(){
        var idJson, idObject;
        if (supports_local_storage()) {
          // read from local storage
          idJson = window.localStorage.getItem(cred);
        }
        else {
          // read from a cookie
          idJson = cookie(cred);
        }
        if (idJson && idJson != "null" && idJson.length > 4) {
          idObject = JSON.parse(idJson);
          esriId.initialize(idObject);
        }
        else {
          // console.log("didn't find anything to load :(");
        }
      }
      function storeCredentials(){
        // make sure there are some credentials to persist
        if (esriId.credentials.length === 0) {
          return;
        }
        // serialize the ID manager state to a string
        var idString = JSON.stringify(esriId.toJson());
        // store it client side
        if (supports_local_storage()) {
          // use local storage
          window.localStorage.setItem(cred, idString);
          // console.log("wrote to local storage");
        }
        else {
          // use a cookie
          cookie(cred, idString, {expires: 1});
          // console.log("wrote a cookie :-/");
        }
      }
      function supports_local_storage(){
        try {
          return "localStorage" in window && window["localStorage"] !== null;
        } catch (e) {
          return false;
        }
      }
    // END OF CREDENTIALS
    
    dojo.addOnLoad(init);
  });
</script>
</head>

<!-- START OF PAGE LAYOUT -->
<body class="claro">
    <div id="printButton"></div>
    <!--<input type="button" id="printButton" value="Print" onclick="print()">-->
    <div id="content" dojotype="dijit.layout.BorderContainer" design="headline" gutters="true" style="width: 800px; height: 800px; margin: 0;">
      <div id="mapdiv" dojotype="dijit.layout.ContentPane" region="center" style="overflow:hidden;"></div>
    </div>
</body>
<!-- END OF PAGE LAYOUT -->
</html>‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍

View solution in original post

10 Replies
BenElan
Esri Contributor

Hi Claire,

Take a look at this sample using the print widget:

Print | ArcGIS API for JavaScript 3.29 

The documentation is here:

Print | API Reference | ArcGIS API for JavaScript 3.29 

0 Kudos
Claire_Peterson
Occasional Contributor

Hi Ben,

I have been reading through the API Reference page and example for the past week but for some reason, I have been unable to implement this. I am a novice when it comes to JS so I may not be fully understanding how to set this up.

0 Kudos
BenElan
Esri Contributor

If you have a specific question or if there is part of the sample that is confusing to you I can try to help.

0 Kudos
Claire_Peterson
Occasional Contributor

I certainly appreciate that! 

In the example I have all the same required modules and functions in my script along with the parser.parse() and esriConfig.defaults.io.proxyUrl = "/proxy/"; is the only other thing that needs to be added the print dijit code below? 

// print dijit
        app
.printer = new Print({
          map
: app.map,
          url
: "https://sampleserver6.arcgisonline.com/arcgis/rest/services/Utilities/PrintingTools/GPServer/Export%20Web%20Map%20Task"
       
}, dom.byId("printButton"));
        app
.printer.startup();

Is var app = {}; and the app. prefix for printer necessary? 

0 Kudos
BenElan
Esri Contributor

In this example they are just creating an 'app' object to organize the different parts of their code. It is not necessary, however if you remove the 'app' declaration you would also need to remove it throughout the rest of the code.

In terms of the url, we do not recommend using sampleserver6 in production. The server is used for testing and is not reliable. I would use this one:

https://utility.arcgisonline.com/arcgis/rest/services/Utilities/PrintingTools/GPServer/Export%20Web%...

So the new snippet would be:

// print dijit
var printer = new Print({
    map: map,
    url: "https://utility.arcgisonline.com/arcgis/rest/services/Utilities/PrintingTools/GPServer/Export%20Web%20Map%20Task"
}, dom.byId("printButton"));

printer.startup();‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍

In terms of the proxy, it should work without one. If you have any other questions let me know. Posting your code would be helpful if that is an option for you.

Claire_Peterson
Occasional Contributor

Hi Ben - thank you so much for clarifying this. It's strange but as soon as I add

  // print dijit
    var printer = new Print({
        map: map,
        url: "https://utility.arcgisonline.com/arcgis/rest/services/Utilities/PrintingTools/GPServer/Export%20Web%20Map%20Task"
    }, dom.byId("printButton"));
    printer.startup();‍‍‍‍‍‍

it seems to bust my map and I get an error TypeError: dom.byId is not a function

It's a bit long but below is what I have so far

<html>
<head>
  <meta charset="utf-8" />
  <meta name="viewport" content="initial-scale=1, maximum-scale=1, user-scalable=no" />
  <title>MISIN Treatment Tracker: Print</title>
  <link rel="stylesheet" href="https://js.arcgis.com/3.29/dijit/themes/claro/claro.css">
  <link rel="stylesheet" href="https://js.arcgis.com/3.29/esri/css/esri.css">
<!--js scripts to print map-->
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.4.1/jquery.min.js"></script>
<script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/jspdf/1.3.2/jspdf.min.js"></script>
<script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/html2canvas/0.4.1/html2canvas.js"></script>
<script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/javascript-canvas-to-blob/3.15.0/js/canvas-to-blob.js"></script>
<script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/FileSaver.js/1.3.8/FileSaver.js"></script>
<!--end print scripts-->
<style>
@media print {
  #printButton {
    display: none;
  }
}
</style>
<!-- START ESRI MAP SCRIPT -->
<script>var dojoConfig = { parseOnLoad: true }</script>
<script src="https://js.arcgis.com/3.29/"></script>
<script>
var theMap;
var cred = "esri_jsapi_id_manager_data";
var symbol, infoTemplate;
var OID;
require([
  "esri/map",
  "esri/SpatialReference",
  "esri/layers/ArcGISTiledMapServiceLayer",
  "esri/layers/ArcGISDynamicMapServiceLayer",
  "esri/layers/FeatureLayer",
  "esri/layers/ImageParameters",
  "esri/symbols/SimpleMarkerSymbol",
  "esri/symbols/SimpleLineSymbol",
  "esri/symbols/SimpleFillSymbol",
  "esri/layers/LayerDrawingOptions",
  "esri/layers/LabelLayer",
  "esri/layers/LabelClass",
  "esri/symbols/TextSymbol",
  "esri/renderers/SimpleRenderer",
  "esri/graphic",
  "esri/InfoTemplate",
  "esri/urlUtils",
  "esri/arcgis/utils",
  "esri/graphicsUtils",
  "esri/dijit/Legend",
  "esri/dijit/Scalebar",
  "esri/dijit/Print",
  "esri/tasks/query",
  "esri/tasks/QueryTask",
  "esri/tasks/PrintTask",
  "esri/tasks/PrintParameters",
  "esri/tasks/PrintTemplate",
  "esri/request",
  "esri/config",
  "esri/geometry/Extent",
  "esri/IdentityManager",
  "esri/lang",
  "dojo/_base/array",
  "dojo/_base/Color",
  "dojo/_base/unload",
  "dojo/cookie",
  "dojo/json",
  "dojo/_base/json",
  "dojo/parser",
  "dojo/dom-construct",
  "dojo/dom-class",
  "dojo/dom",
  "dojo/on",
  "dojo/domReady!",
  "dijit/layout/BorderContainer",
  "dijit/layout/ContentPane",
  "dijit/form/Button"
], function(
  Map,
  //MapView,
  SpatialReference,
  ArcGISTiledMapServiceLayer,
  ArcGISDynamicMapServiceLayer,
  FeatureLayer,
  ImageParameters,
  SimpleMarkerSymbol,
  SimpleLineSymbol,
  SimpleFillSymbol,
  LayerDrawingOptions,
  LabelLayer,
  LabelClass,
  TextSymbol,
  SimpleRenderer,
  Graphic,
  InfoTemplate,
  urlUtils,
  arcgisUtils,
  graphicsUtils,
  Legend,
  Scalebar,
  Print,
  Query,
  QueryTask,
  PrintTask,
  PrintParameters,
  PrintTemplate,
  esriRequest,
  esriConfig,
  Extent,
  esriId,
  esriLang,
  arrayUtils,
  Color,
  baseUnload,
  cookie,
  JSON,
  parser,
  domConstruct,
  domClass,
  dom,
  on,
  BorderContainer,
  ContentPane,
  Button
  ){
    function init()
    {
      // store credentials/serverInfos before the page unloads
     baseUnload.addOnUnload(storeCredentials);
     // look for credentials in local storage
     loadCredentials();
     //parser.parse();
     esriConfig.defaults.io.proxyUrl = "/proxy/";
     // START OF ESRI WEBMAP CREATION
    //create the map
    theMap = new Map("mapdiv", {
      basemap:"topo",
      showLabels: true,
      });
      
    //Disable Map Navigation
    theMap.on("load", function() {
    theMap.disableMapNavigation();
    theMap.hideZoomSlider();
  });

    // print dijit
        var printer = new Print({
            map: theMap,
url: "https://utility.arcgisonline.com/arcgis/rest/services/Utilities/PrintingTools/GPServer/Export%20Web%20Map%20Task"
        }, dom.byId("printButton"));
        printer.startup();

    // Create labels for the National Wetlands Inventory Layer
    var labelField = "WETLAND_TYPE"
    var wetlandsColor = new Color ("#0E881B");
    var wetlandsLine = new SimpleLineSymbol("solid", wetlandsColor, 1.5);
    var wetlandsRenderer = new SimpleRenderer(wetlandsLine);
    var wetlandsLabel = new TextSymbol().setColor(wetlandsColor);
    wetlandsLabel.font.setSize("10pt");
    wetlandsLabel.font.setFamily("arial");
    var json = {
      "labelExpressionInfo": {"value": "{WETLAND_TYPE}"}
    };

    //create instance of LabelClass (note: multiple LabelClasses can also be passed in as an array)
    var labelClass = new LabelClass(json);
    labelClass.symbol = wetlandsLabel;

    //Add National Wetlands Inventory
    var wetlands = new FeatureLayer("https://gisago.mcgi.state.mi.us/arcgis/rest/services/OpenData/hydro/MapServer/18");
    wetlands.setRenderer(wetlandsRenderer)
    wetlands.setLabelingInfo([ labelClass ]);
    theMap.addLayer(wetlands);

    //Use the ImageParameters to set map service layer definitions and map service visible layers before adding to the client map.
    var imageParameters = new ImageParameters();

    //only certain layers to be visible. This can only be done with a dynamic map service and it does impact performance. Cached map services are recommended.
    imageParameters.layerIds = [2];
    imageParameters.layerOption = ImageParameters.LAYER_OPTION_SHOW;
    imageParameters.transparent = true;

    //construct ArcGISDynamicMapServiceLayer with imageParameters from above
    var dynamicMapServiceLayer = new ArcGISDynamicMapServiceLayer("https://fuzzy.asets.msu.edu/arcgis/rest/services/MISIN/misin_treatments/MapServer",
    {"opacity": 0.0},
    {"imageParameters": imageParameters});
    theMap.addLayer(dynamicMapServiceLayer);

    //build query task
    var queryTask = new QueryTask("https://fuzzy.asets.msu.edu/arcgis/rest/services/MISIN/misin_treatments/MapServer/2");
    //build query filter
    var query = new Query();
    query.returnGeometry = true;
    query.outFields = ["*"];
    //create symbol for selected features
    symbol = new SimpleFillSymbol(SimpleFillSymbol.STYLE_SOLID,
  new SimpleLineSymbol(SimpleLineSymbol.STYLE_SOLID,
  new dojo.Color([64,124,248]), 2),new dojo.Color([189,209,253]));

    //pass the url parameters.
    var urlObject = urlUtils.urlToObject(window.location.href);
    if (urlObject.query)
    {
      if (urlObject.query.id)
      { OID = urlObject.query.id; }
    //set query based on the parameters
    var treatmentid = "OBJECTID = '" + OID + "'";
    query.where = treatmentid;

    //execute query and call showResults on completion
    //queryTask.execute(query,showResults);
    }
    //Execute task and call showResults on completion
    queryTask.execute(query, showResults);
    }
    function showResults(featureSet)
    {
    //remove all graphics on the maps graphics layer
    theMap.graphics.clear();
    theMap.infoWindow.hide();

    //QueryTask returns a featureSet.  Loop through features in the featureSet and add them to the map.
    //Performance enhancer - assign featureSet array to a single variable.
    var resultFeatures = featureSet.features;
    for (var i=0, il=resultFeatures.length; i<il; i++)
    {
    //Get the current feature from the featureSet. Feature is a graphic
    var graphic = resultFeatures[i];
    graphic.setSymbol(symbol);
    //Set the infoTemplate.
    graphic.setInfoTemplate(infoTemplate);
    //Add graphic to the map graphics layer.
    theMap.graphics.add(graphic);
    }

    //Zoom to the extent of the graphics
    var myFeatureExtent = esri.graphicsExtent(resultFeatures);
    theMap.setExtent(myFeatureExtent.getExtent().expand(3));
    //Refresh the URL with the currently selected parcel
    window.history.pushState(null,null,"?id=" + graphic.attributes.OBJECTID);
    }

    // END OF ESRI MAP CREATION

    // STORE CREDENTIALS
    function loadCredentials(){
        var idJson, idObject;
        if (supports_local_storage()) {
          // read from local storage
          idJson = window.localStorage.getItem(cred);
        }
        else {
          // read from a cookie
          idJson = cookie(cred);
        }
        if (idJson && idJson != "null" && idJson.length > 4) {
          idObject = JSON.parse(idJson);
          esriId.initialize(idObject);
        }
        else {
          // console.log("didn't find anything to load :(");
        }
      }
      function storeCredentials(){
        // make sure there are some credentials to persist
        if (esriId.credentials.length === 0) {
          return;
        }
        // serialize the ID manager state to a string
        var idString = JSON.stringify(esriId.toJson());
        // store it client side
        if (supports_local_storage()) {
          // use local storage
          window.localStorage.setItem(cred, idString);
          // console.log("wrote to local storage");
        }
        else {
          // use a cookie
          cookie(cred, idString, {expires: 1});
          // console.log("wrote a cookie :-/");
        }
      }
      function supports_local_storage(){
        try {
          return "localStorage" in window && window["localStorage"] !== null;
        } catch (e) {
          return false;
        }
      }
    // END OF CREDENTIALS
    
    dojo.addOnLoad(init);
  });
</script>
</head>

<!-- START OF PAGE LAYOUT -->
<body class="claro">
    <div id="printButton"></div>
    <!--<input type="button" id="printButton" value="Print" onclick="print()">-->
    <div id="content" dojotype="dijit.layout.BorderContainer" design="headline" gutters="true" style="width: 800px; height: 800px; margin: 0;">
      <div id="mapdiv" dojotype="dijit.layout.ContentPane" region="center" style="overflow:hidden;"></div>
    </div>
</body>
<!-- END OF PAGE LAYOUT -->
</html>‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍
0 Kudos
KenBuja
MVP Esteemed Contributor

Your function arguments aren't matching your require modules. At line 68, you call "dojo/_base/json" but don't have a corresponding function argument. At line 74, you do the same with "dojo/domReady!". Since domReady! doesn't need a function argument, it is put after any modules that do need a function argument.

BenElan
Esri Contributor

This worked for me

<html>
<head>
  <meta charset="utf-8" />
  <meta name="viewport" content="initial-scale=1, maximum-scale=1, user-scalable=no" />
  <title>MISIN Treatment Tracker: Print</title>
  <link rel="stylesheet" href="https://js.arcgis.com/3.29/dijit/themes/claro/claro.css">
  <link rel="stylesheet" href="https://js.arcgis.com/3.29/esri/css/esri.css">
<!--js scripts to print map-->
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.4.1/jquery.min.js"></script>
<script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/jspdf/1.3.2/jspdf.min.js"></script>
<script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/html2canvas/0.4.1/html2canvas.js"></script>
<script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/javascript-canvas-to-blob/3.15.0/js/canvas-to-blob.js"></script>
<script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/FileSaver.js/1.3.8/FileSaver.js"></script>
<!--end print scripts-->
<style>
@media print {
  #printButton {
    display: none;
  }
}
</style>
<!-- START ESRI MAP SCRIPT -->
<script>var dojoConfig = { parseOnLoad: true }</script>
<script src="https://js.arcgis.com/3.29/"></script>
<script>
var theMap;
var cred = "esri_jsapi_id_manager_data";
var symbol, infoTemplate;
var OID;
require([
  "esri/map",
  "esri/SpatialReference",
  "esri/layers/ArcGISTiledMapServiceLayer",
  "esri/layers/ArcGISDynamicMapServiceLayer",
  "esri/layers/FeatureLayer",
  "esri/layers/ImageParameters",
  "esri/symbols/SimpleMarkerSymbol",
  "esri/symbols/SimpleLineSymbol",
  "esri/symbols/SimpleFillSymbol",
  "esri/layers/LayerDrawingOptions",
  "esri/layers/LabelLayer",
  "esri/layers/LabelClass",
  "esri/symbols/TextSymbol",
  "esri/renderers/SimpleRenderer",
  "esri/graphic",
  "esri/InfoTemplate",
  "esri/urlUtils",
  "esri/arcgis/utils",
  "esri/graphicsUtils",
  "esri/dijit/Legend",
  "esri/dijit/Scalebar",
  "esri/dijit/Print",
  "esri/tasks/query",
  "esri/tasks/QueryTask",
  "esri/tasks/PrintTask",
  "esri/tasks/PrintParameters",
  "esri/tasks/PrintTemplate",
  "esri/request",
  "esri/config",
  "esri/geometry/Extent",
  "esri/IdentityManager",
  "esri/lang",
  "dojo/_base/array",
  "dojo/_base/Color",
  "dojo/_base/unload",
  "dojo/cookie",
  "dojo/json",
  //"dojo/_base/json",
  "dojo/parser",
  "dojo/dom-construct",
  "dojo/dom-class",
  "dojo/dom",
  "dojo/on",
  "dijit/layout/BorderContainer",
  "dijit/layout/ContentPane",
  "dijit/form/Button",
  "dojo/domReady!",
], function(
  Map,
  //MapView,
  SpatialReference,
  ArcGISTiledMapServiceLayer,
  ArcGISDynamicMapServiceLayer,
  FeatureLayer,
  ImageParameters,
  SimpleMarkerSymbol,
  SimpleLineSymbol,
  SimpleFillSymbol,
  LayerDrawingOptions,
  LabelLayer,
  LabelClass,
  TextSymbol,
  SimpleRenderer,
  Graphic,
  InfoTemplate,
  urlUtils,
  arcgisUtils,
  graphicsUtils,
  Legend,
  Scalebar,
  Print,
  Query,
  QueryTask,
  PrintTask,
  PrintParameters,
  PrintTemplate,
  esriRequest,
  esriConfig,
  Extent,
  esriId,
  esriLang,
  arrayUtils,
  Color,
  baseUnload,
  cookie,
  JSON,
  parser,
  domConstruct,
  domClass,
  dom,
  on,
  BorderContainer,
  ContentPane,
  Button
  ){
    function init()
    {
      // store credentials/serverInfos before the page unloads
     baseUnload.addOnUnload(storeCredentials);
     // look for credentials in local storage
     loadCredentials();
     //parser.parse();
     esriConfig.defaults.io.proxyUrl = "/proxy/";
     // START OF ESRI WEBMAP CREATION
    //create the map
    theMap = new Map("mapdiv", {
      basemap:"topo",
      showLabels: true,
      });
      
    //Disable Map Navigation
    theMap.on("load", function() {
    theMap.disableMapNavigation();
    theMap.hideZoomSlider();
  });

    // print dijit
        var printer = new Print({
            map: theMap,
url: "https://utility.arcgisonline.com/arcgis/rest/services/Utilities/PrintingTools/GPServer/Export%20Web%20Map%20Task"
        }, dom.byId("printButton"));
        printer.startup();

    // Create labels for the National Wetlands Inventory Layer
    var labelField = "WETLAND_TYPE"
    var wetlandsColor = new Color ("#0E881B");
    var wetlandsLine = new SimpleLineSymbol("solid", wetlandsColor, 1.5);
    var wetlandsRenderer = new SimpleRenderer(wetlandsLine);
    var wetlandsLabel = new TextSymbol().setColor(wetlandsColor);
    wetlandsLabel.font.setSize("10pt");
    wetlandsLabel.font.setFamily("arial");
    var json = {
      "labelExpressionInfo": {"value": "{WETLAND_TYPE}"}
    };

    //create instance of LabelClass (note: multiple LabelClasses can also be passed in as an array)
    var labelClass = new LabelClass(json);
    labelClass.symbol = wetlandsLabel;

    //Add National Wetlands Inventory
    var wetlands = new FeatureLayer("https://gisago.mcgi.state.mi.us/arcgis/rest/services/OpenData/hydro/MapServer/18");
    wetlands.setRenderer(wetlandsRenderer)
    wetlands.setLabelingInfo([ labelClass ]);
    theMap.addLayer(wetlands);

    //Use the ImageParameters to set map service layer definitions and map service visible layers before adding to the client map.
    var imageParameters = new ImageParameters();

    //only certain layers to be visible. This can only be done with a dynamic map service and it does impact performance. Cached map services are recommended.
    imageParameters.layerIds = [2];
    imageParameters.layerOption = ImageParameters.LAYER_OPTION_SHOW;
    imageParameters.transparent = true;

    //construct ArcGISDynamicMapServiceLayer with imageParameters from above
    var dynamicMapServiceLayer = new ArcGISDynamicMapServiceLayer("https://fuzzy.asets.msu.edu/arcgis/rest/services/MISIN/misin_treatments/MapServer",
    {"opacity": 0.0},
    {"imageParameters": imageParameters});
    theMap.addLayer(dynamicMapServiceLayer);

    //build query task
    var queryTask = new QueryTask("https://fuzzy.asets.msu.edu/arcgis/rest/services/MISIN/misin_treatments/MapServer/2");
    //build query filter
    var query = new Query();
    query.returnGeometry = true;
    query.outFields = ["*"];
    //create symbol for selected features
    symbol = new SimpleFillSymbol(SimpleFillSymbol.STYLE_SOLID,
  new SimpleLineSymbol(SimpleLineSymbol.STYLE_SOLID,
  new dojo.Color([64,124,248]), 2),new dojo.Color([189,209,253]));

    //pass the url parameters.
    var urlObject = urlUtils.urlToObject(window.location.href);
    if (urlObject.query)
    {
      if (urlObject.query.id)
      { OID = urlObject.query.id; }
    //set query based on the parameters
    var treatmentid = "OBJECTID = '" + OID + "'";
    query.where = treatmentid;

    //execute query and call showResults on completion
    //queryTask.execute(query,showResults);
    }
    //Execute task and call showResults on completion
    queryTask.execute(query, showResults);
    }
    function showResults(featureSet)
    {
    //remove all graphics on the maps graphics layer
    theMap.graphics.clear();
    theMap.infoWindow.hide();

    //QueryTask returns a featureSet.  Loop through features in the featureSet and add them to the map.
    //Performance enhancer - assign featureSet array to a single variable.
    var resultFeatures = featureSet.features;
    for (var i=0, il=resultFeatures.length; i<il; i++)
    {
    //Get the current feature from the featureSet. Feature is a graphic
    var graphic = resultFeatures[i];
    graphic.setSymbol(symbol);
    //Set the infoTemplate.
    graphic.setInfoTemplate(infoTemplate);
    //Add graphic to the map graphics layer.
    theMap.graphics.add(graphic);
    }

    //Zoom to the extent of the graphics
    var myFeatureExtent = esri.graphicsExtent(resultFeatures);
    theMap.setExtent(myFeatureExtent.getExtent().expand(3));
    //Refresh the URL with the currently selected parcel
    window.history.pushState(null,null,"?id=" + graphic.attributes.OBJECTID);
    }

    // END OF ESRI MAP CREATION

    // STORE CREDENTIALS
    function loadCredentials(){
        var idJson, idObject;
        if (supports_local_storage()) {
          // read from local storage
          idJson = window.localStorage.getItem(cred);
        }
        else {
          // read from a cookie
          idJson = cookie(cred);
        }
        if (idJson && idJson != "null" && idJson.length > 4) {
          idObject = JSON.parse(idJson);
          esriId.initialize(idObject);
        }
        else {
          // console.log("didn't find anything to load :(");
        }
      }
      function storeCredentials(){
        // make sure there are some credentials to persist
        if (esriId.credentials.length === 0) {
          return;
        }
        // serialize the ID manager state to a string
        var idString = JSON.stringify(esriId.toJson());
        // store it client side
        if (supports_local_storage()) {
          // use local storage
          window.localStorage.setItem(cred, idString);
          // console.log("wrote to local storage");
        }
        else {
          // use a cookie
          cookie(cred, idString, {expires: 1});
          // console.log("wrote a cookie :-/");
        }
      }
      function supports_local_storage(){
        try {
          return "localStorage" in window && window["localStorage"] !== null;
        } catch (e) {
          return false;
        }
      }
    // END OF CREDENTIALS
    
    dojo.addOnLoad(init);
  });
</script>
</head>

<!-- START OF PAGE LAYOUT -->
<body class="claro">
    <div id="printButton"></div>
    <!--<input type="button" id="printButton" value="Print" onclick="print()">-->
    <div id="content" dojotype="dijit.layout.BorderContainer" design="headline" gutters="true" style="width: 800px; height: 800px; margin: 0;">
      <div id="mapdiv" dojotype="dijit.layout.ContentPane" region="center" style="overflow:hidden;"></div>
    </div>
</body>
<!-- END OF PAGE LAYOUT -->
</html>‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍‍
Claire_Peterson
Occasional Contributor

Ken Buja‌ and Ben Elan‌ - I can't thank you enough for taking the time to look over my code and Ben, I was able to get a printout! I would have never figured out that the positioning of the "dojo/domReady!" module would have made a difference... At least I was close! I believe the "dojo/_base/json" that you pointed out Ken was left over from another printing process I was trying but had forgotten to remove it. 

I don't mean to bother you both with another question but now that I have a printout with the .png URL, can this print process be called in the background versus a button? 

0 Kudos