-----------------------------------

Acquista i software ArcGIS tramite Studio A&T srl, rivenditore autorizzato dei prodotti Esri.

I migliori software GIS, il miglior supporto tecnico!

I migliori software GIS, il miglior supporto tecnico!
Azienda operante nel settore GIS dal 2001, specializzata nell’utilizzo della tecnologia ArcGIS e aderente ai programmi Esri Italia Business Network ed Esri Partner Network

-----------------------------------



Visualizzazione post con etichetta SQL Server. Mostra tutti i post
Visualizzazione post con etichetta SQL Server. Mostra tutti i post

domenica 28 novembre 2010

SQL Server Reporting services Map & ArcGIS Server

Con la nuova versione di SQL Server 2008 R2, possiamo visualizzare mappe nelle report che distribuiamo con RS (anche con la versione Express).

Questo è possibile grazie al nuovo controllo map. Qui potete trovare maggiori dettagli su tale controllo.

Contestualmente all'aggiunta in ArcGIS Server dei query layer,  possiamo effettuare una sorta di integrazione tra ArcGIS Server ed il controllo di mappa di RS senza utilizzare gli shapefile.

In questo video illustro una possibile integrazione:


Code:

<%@ WebHandler Language="C#" Class="rsMap" %>
 
using System;
using System.Web;
//Author: Domenico Ciavarella
//www.studioat.it
public class rsMap : IHttpHandler {
 
 public void ProcessRequest (HttpContext context) {
  
  bool isJson = false;
  bool isPrettyJson = false;
  string format = null;
  if (context.Request.QueryString["f"] != null)
  {
   format = context.Request.QueryString["f"].ToLower();
   if (format == "json" || format == "pjson")
   {
    isJson = true;
    isPrettyJson = format == "pjson";
   }
  }
 
  
  
  reportExecution.ReportExecutionService rs = new reportExecution.ReportExecutionService();
  rs.Credentials = new System.Net.NetworkCredential(System.Configuration.ConfigurationManager.AppSettings.Get("userReport"), System.Configuration.ConfigurationManager.AppSettings.Get("passwordReport"), System.Configuration.ConfigurationManager.AppSettings.Get("domain"));
  
  // Render arguments
  byte[] result = null;
  string reportPath = "/rsMappe/rsMap";
  string formatOutput = "PDF";
  string historyID = null;
 
  string encoding;
  string mimeType;
  string extension;
  reportExecution.Warning[] warnings = null;
  string[] streamIDs = null;
 
 
  
 
 
  reportExecution.ExecutionInfo execInfo = new reportExecution.ExecutionInfo();
  reportExecution.ExecutionHeader execHeader = new reportExecution.ExecutionHeader();
 
  rs.ExecutionHeaderValue = execHeader;
 
  execInfo = rs.LoadReport(reportPath, historyID);
  
  String SessionId = rs.ExecutionHeaderValue.ExecutionID;
 
  string oidValue = context.Server.HtmlEncode(context.Request.QueryString["oid"]);
  
  if (string.IsNullOrEmpty(oidValue))
  {
   context.Response.Write("Parametri non passati!");
   return;
  }
  
 
 
 
  reportExecution.ParameterValue[] parameters = new reportExecution.ParameterValue[1 ];
 
    
  parameters[0] = new reportExecution.ParameterValue();
  parameters[0].Name = "pFID";
  parameters[0].Value = oidValue;
  
  rs.SetExecutionParameters(parameters, "it-IT");
   
  result = rs.Render(formatOutput, nullout extension, out encoding, out mimeType, out warnings, out streamIDs);
 
 
  if (isJson)
  {
   string fileName = "_ags_" + Guid.NewGuid().ToString() + ".pdf";
   string pathfileName = @"c:\arcgisserver\arcgisoutput\" + fileName;
   string urlfileName = "http://localhost/arcgisoutput/" + fileName;
   using (System.IO.FileStream stream = System.IO.File.OpenWrite(pathfileName))
   {
    stream.Write(result, 0, result.Length);
   }
 
   GenerateJson(context, new Result() { url = urlfileName }, isPrettyJson);
   return;
  }
  
  
  context.Response.ClearContent();
  context.Response.AppendHeader("content-length", result.Length.ToString());
  context.Response.ContentType = "application/pdf";
  context.Response.BinaryWrite(result);
  context.Response.Flush();
  context.Response.Close();
 }
 
 public bool IsReusable {
  get {
   return false;
  }
 }
 
 
 private static void GenerateJson(HttpContext context, Result result, bool isPrettyJson)
 {
  context.Response.ContentType = "text/plain";
  string newLine = "\n";
  string tab = " ";
  if (!isPrettyJson)
  {
   newLine = tab = "";
  }
  context.Response.Write(string.Format("{{\"results\": {0}", newLine, tab));
 
  context.Response.Write(string.Format("{2}{1}{2}{2}{{\"url\":\"{0}\"}}{1}", result.url, newLine, tab));
    
  context.Response.Write(string.Format("{0}}}", newLine, tab));
 }
 
 public struct Result {
  public string url;
 }
 
 
}


page HTML:

<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01//EN" "http://www.w3.org/TR/html4/strict.dtd">
<html>
<head>
<meta http-equiv="X-UA-Compatible" content="IE=7" />
  <title>ArcGIS JavaScript API: LimitiComuni</title>
<style type="text/css">
  @import "http://serverapi.arcgisonline.com/jsapi/arcgis/2.1/js/dojo/dijit/themes/tundra/tundra.css";
htmlbody { height100%width100%margin0padding0; }
      .tundra .dijitSplitContainer-dijitContentPane.tundra .dijitBorderContainer-dijitContentPane#navtable { 
        PADDING-BOTTOM5pxMARGIN0px 0px 3pxPADDING-TOP0pxBORDER-BOTTOM#000 1px solidBORDER-TOP#000 1px solidBACKGROUND-COLOR#E5EFF7;
      }
      .tundra .dijitSplitContainer-dijitContentPane.tundra .dijitBorderContainer-dijitContentPane#map {
        overflow:hiddenborder:solid 1px blackpadding0;
      }
      #breadcrumbs {
        PADDING-RIGHT0pxPADDING-LEFT11pxFONT-SIZE0.8emFONT-WEIGHTboldPADDING-BOTTOM5pxMARGIN0px 0px 3pxPADDING-TOP0px;
      }
      #help {
        PADDING-RIGHT11pxPADDING-LEFT0pxFONT-SIZE0.70emPADDING-BOTTOM5pxMARGIN0px 0px 3pxPADDING-TOP3px</style>
<script type="text/javascript" src="http://serverapi.arcgisonline.com/jsapi/arcgis?v=2.1"></script>
<script type="text/javascript">
    dojo.require("esri.map");
    dojo.require("dijit.layout.ContentPane");
    dojo.require("dijit.layout.BorderContainer");
    dojo.require("dijit.Dialog");
 
    var map;
    var printDlg;
 
    function Init() {
        dojo.style(dojo.byId("map"), { width: dojo.contentBox("map").w + "px", height: (esri.documentBox.h - dojo.contentBox("navTable").h - 40) + "px" });
        var initExtent = new esri.geometry.Extent({ "xmin": 6.55059928850006, "ymin": 45.0006208151578,
            "xmax": 8.22229873550003, "ymax": 45.6702338525465, "spatialReference": { "wkid": 4326 }
        });
        map = new esri.Map("map", { extent: initExtent });
        
        printDlg = new dijit.Dialog({
            title: "Stampa",
            style: "width: 825px; height: 650px"
        });
   
        var layer = new esri.layers.ArcGISDynamicMapServiceLayer("http://localhost/ArcGIS/rest/services/LimitiComuni/MapServer", { "opacity": 0.5 });
        var layerBaseMap = new esri.layers.ArcGISTiledMapServiceLayer("http://server.arcgisonline.com/ArcGIS/rest/services/ESRI_StreetMap_World_2D/MapServer");
        map.addLayer(layerBaseMap);
        map.addLayer(layer);
        var resizeTimer;
        dojo.connect(map, 'onLoad'function (theMap) {
            dojo.connect(map, "onClick", doIdentify);
 
            identifyTask = new esri.tasks.IdentifyTask("http://localhost/ArcGIS/rest/services/LimitiComuni/MapServer");
 
            identifyParams = new esri.tasks.IdentifyParameters();
            identifyParams.tolerance = 3;
            identifyParams.returnGeometry = false;
            identifyParams.layerIds = [0];
            identifyParams.layerOption = esri.tasks.IdentifyParameters.LAYER_OPTION_ALL;
            identifyParams.width = map.width;
            identifyParams.height = map.height;
            
            dojo.connect(dijit.byId('map'), 'resize'function () {
                clearTimeout(resizeTimer);
                resizeTimer = setTimeout(function () {
                    map.resize();
                    map.reposition();
                }, 500);
            });
        });
    }
    dojo.addOnLoad(Init);
 
 
    function doIdentify(evt) {
        identifyParams.geometry = evt.mapPoint;
        identifyParams.mapExtent = map.extent;
        identifyTask.execute(identifyParams, function (idResults) { addToMap(idResults, evt); });
    }
    function addToMap(idResults, evt) {
        var idResult = idResults[0];
        print(idResult.feature.attributes.FID);
    }
 
    function print(id) {
   var url = esri.urlToObject("http://localhost/rsMap/rsMap.ashx?f=json&oidIndirizzo=" + id);

            var requestHandle = esri.request({
                url: url.path,
                content: url.query,
                handleAs: "json",
                load: function (data) {
                    printDlg.attr("content", "<div><object data='" + data.results.url + "' type='application/pdf' width='800' height='600'></object></div>");
                    printDlg.show();
                },
                error: function (error) {
                    alert("Errore di stampa");
                }
            });
}
 
 
</script>
</head>
<body class="tundra">
 
<table style="width:100%">
<tr>
<td>
<table id="navTable" width="100%">
<tbody>
<tr valign="top">
<td id="breadcrumbs">
ArcGIS JavaScript API: LimitiComuni
</td>
<td align="right" id="help">
Built using the  <a href="http://resources.esri.com/arcgisserver/apis/javascript/arcgis">ArcGIS JavaScript API</a>
</td>
</tr>
</tbody>
</table>
 
</td>
</tr>
</table>
<div id="map" style="margin:auto;width:97%;border:1px solid #000;"></div>
</body>
</html>

sabato 13 febbraio 2010

Sql server 2008: SQL Server Geospatial Services WMS

Volevo segnalarvi un interessante progetto in corso su codeplex per esporre i dati sql server in servizi wms, wfs, wps, geojson e tile.

In questo post ho provato ad utilizzare il servizio WMS esposto da SQL server 2008 con un client Silverlight servendomi  dell'esempio ESRI di Silverlight (esempio di subclassing della classe astratta DynamicMapServiceLayer).

Comunque, per queste due soluzioni, ho dovuto fare alcune piccole correzioni riguardo alla gestione del simbolo di separatore decimale in base alla cultura. Se avete le impostazioni internazionali sull'Inglese, potete tranquillamente utilizzare le versioni originali.

Da Visual Studio 2008 aprite il progetto OgcWebServices e poi includete l'altro progetto (GeoSpatialServices). Da Solution Explorer visualizzate i file nascosti (Show Hidden Files) e in App_Data fate doppio click sul file TestGeospatialServicesDatabase.mdf (in questo modo fate un attach del file in sql server 2008 express). A questo punto, sempre in App_Data, aprite il file WFSConfiguration.xml e modificate la vostra connessione al database.



Una volta compilata ed eseguita la soluzione, visualizzerete una pagina con dei link di test:
il secondo link visualizza l'intero layer con un SLD di default




il terzo link visualizza l'intero layer con un SLD specifico (SLD di nome region)



Ora lasciamo attivo il progetto, in modo che sia in grado di ricevere le chiamate, ed apriamo il progetto wms (cioè l'esempio di ESRI); poi compiliamo ed eseguiamo la soluzione


Se non specificate lo style nello XAML dovreste vedere il vostro layer sovrapposto allo StreetMap World 2D di ESRI.


se, in caso contrario, specificate l'SLD:

<esriWMS:WMSMapServiceLayer ID="AGSWMSLayer"
                     Url="http://localhost:49241/service.wms"                    
                     SkipGetCapabilities="False"
                     Layers="world_admin" Version="1.3.0" Opacity="0.7" Styles="region"/>

dovreste vedere:



Scarica qui la soluzione

mercoledì 4 novembre 2009

Google encoded polygons da SQL Server 2008

Pubblico un proof of concept per come codificare poligoni o polilinee in google maps leggendo dati da sql server 2008.
In questo link potete trovare l'articolo di Google che spiega algoritmo mentre una spiegazione più approfondita potete trovarla in questi due link Encoding algorithm e Description of encoded polylines di Mark McClure.

Inoltre sempre su Google potete testare direttamente online Interactive Polyline Encoder Utility

Nel progetto che vi ho allegato ho utilizzato il js PolylineEncoder che potete trovare qui.

In sintesi ho tradotto in c# la classe PolylineEncoder per poter creare le polilinee & poligoni anche lato server.

Lato server

using System;
using System.Collections.Generic;
using System.Configuration;
using System.Data.SqlClient;
using System.Linq;
using System.Web.Services;
using Microsoft.SqlServer.Types;

//Author: Domenico Ciavarella
//http://www.studioat.it

namespace GoogleEncode
{
    public partial class _Default : System.Web.UI.Page
    {
        protected void Page_Load(object sender, EventArgs e)
        {

        }
        [WebMethod]
        public static List<List<double []>> GetPolygonEncodeClient()
        {
            List<List<double[]>> pts = new List<List<double []>>();
            using (SqlConnection conn = new SqlConnection(ConfigurationManager.ConnectionStrings["GeoConnectionString"].ConnectionString))
            {
                conn.Open();
                string sqlCommandText = "SELECT GEOM FROM LimitiComunali WHERE FID < 20";

                using (SqlCommand sqlCommand = new SqlCommand(sqlCommandText, conn))
                {
                    using (SqlDataReader sdr = sqlCommand.ExecuteReader())
                    {
                        while (sdr.Read())
                        {
                            pts.Add(GetPoints<List<double[]>, double[]>((SqlGeography)(sdr["GEOM"]),(d1,d2) => new double[2]{d1,d2}));
                        }
                    }
                }

            }
            return pts;
        }

        [WebMethod]
        public static Encode[] GetPolygonEncodeServer()
        {
            PolylineEncoder polylineEncoder = new PolylineEncoder();
            IList<Encode> pts = new List<Encode>();

            using (SqlConnection conn = new SqlConnection(ConfigurationManager.ConnectionStrings["GeoConnectionString"].ConnectionString))
            {
                conn.Open();
                string sqlCommandText = "SELECT GEOM FROM LimitiComunali WHERE FID < 20";
                using (SqlCommand sqlCommand = new SqlCommand(sqlCommandText, conn))
                {
                    using (SqlDataReader sdr = sqlCommand.ExecuteReader())
                    {
                        while (sdr.Read())
                        {
                            pts.Add(polylineEncoder.DpEncode(GetPoints<List<Point>,Point>((SqlGeography)(sdr["GEOM"]),(d1,d2) => new Point(d1,d2)).ToArray<Point>()));
                        }
                    }
                }
            }
            return pts.ToArray<Encode>();
        }

        public static T GetPoints<T,U>(SqlGeography sqlGeography, Func<double,double,U> ctor) where T :ICollection<U>, new()
        {
            SqlGeography sqlGeographyExterior = null;

            T list = new T();
            if (sqlGeography.NumRings().Value == 1)
            {
                sqlGeographyExterior = sqlGeography;
            }
            else
            {
                sqlGeographyExterior = sqlGeography.RingN(1);
            }

            SqlGeography sqlGeographyCurrent = null;
            for (int i = 1; i <= sqlGeographyExterior.STNumPoints().Value; i++)
            {
                sqlGeographyCurrent = sqlGeographyExterior.STPointN(i);


                list.Add(ctor(sqlGeographyCurrent.Long.Value, sqlGeographyCurrent.Lat.Value));
            }

            return list;
        }


    }
}



Lato client (decommenta PageMethods.GetPolygonEncodeClient o PageMethods.GetPolygonEncodeServer se rispettivamente vuoi codificare lato client o lato server)

<%@ Page Language="C#" AutoEventWireup="true" CodeBehind="Default.aspx.cs" Inherits="GoogleEncode._Default" %>

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">

<html xmlns="http://www.w3.org/1999/xhtml" >
<head runat="server">
    <title></title>
    <script src="http://maps.google.com/maps?file=api&amp;v=2&amp;key=ABQIAAAAzr2EBOXUKnm_jVnk0OJI7xSosDVG8KKPE1-m51RBrvYughuyMxQ-i1QfUnH94QxWIa6N4U6MouMmBA"
            type="text/javascript"></script>
<script src ="js/PolylineEncoder.js" type="text/javascript"></script>
<script type="text/javascript">
    var map = null;
    function initialize() {
      if (GBrowserIsCompatible()) {
          map = new GMap2(document.getElementById("map_canvas"));
          var mapControl = new GMapTypeControl();
          map.addControl(mapControl);
          map.addControl(new GLargeMapControl());
          var centerat = new GLatLng(45.52, 7.52);
          map.setCenter(centerat, 10);

          //build encode from client
          PageMethods.GetPolygonEncodeClient(onCompleteGetPolygonEncodeClient, onFailureGetPolygonEncode);

          //build encode from server
          //PageMethods.GetPolygonEncodeServer(onCompleteGetPolygonEncodeServer, onFailureGetPolygonEncode);  
      }
    }

    function onCompleteGetPolygonEncodeServer(result, response, context) {
        var plArray = new Array();

        for (i = 0; i < result.length; i++) {

            var polyline = { color: "#0000ff",
                weight: 3,
                opacity: 0.9,
                points: result[i].EncodedPoints,
                levels: result[i].EncodedLevels,
                numLevels: 18,
                zoomFactor: 2
            };
            Array.add(plArray, polyline);

        }
        var polygon = new GPolygon.fromEncoded({polylines: plArray, color: "#0000ff", opacity: 0.9, fill: true, outline: true });
        map.addOverlay(polygon);

    }





    function onCompleteGetPolygonEncodeClient(result, response, context) {

        var plArray = new Array();
        var polygonEncoder = new PolylineEncoder();
        for (i = 0; i < result.length; i++) {
            var pts = PolylineEncoder.pointsToGLatLngs(result[i]);
            var plJSON = polygonEncoder.dpEncodeToJSON(pts, "#0000ff", 3, 0.9);
            Array.add(plArray, plJSON);

        }

        var polygon = new GPolygon.fromEncoded({ polylines: plArray, color: "#0000ff", opacity: 0.9, fill: true, outline: true });
        map.addOverlay(polygon);

    }
    function onFailureGetPolygonEncode(objError) {
        alert(objError.get_message());
    }

    function ColorRandom() {
        return (Math.round(0xFFFFFF * Math.random()).toString(16) + "000000").replace(/([a-f0-9]{6}).+/, "#$1").toUpperCase();
    }

    </script>
  </head>

  <body onload="initialize()" onunload="GUnload()">
  <form id="form1" runat="server">
    <asp:ScriptManager ID="ScriptManager" runat="server"
       EnablePageMethods="true">
       </asp:ScriptManager>
        <div id="map_canvas" style="width: 800px; height: 600px"></div>
    </form>

  </body>

</html>
Scarica qui la soluzione