ArcGIS Server Virtual Earth Tile Server vs. ArcIMS
February 4, 2008
using System;
using System.Text;
using ArcDeveloper.TileServer.Interfaces;
using System.Net;
using System.IO;
using System.Xml;
using System.Drawing;
using System.Drawing.Imaging;
namespace ArcDeveloper.TileServer.ArcIMS
{
public class ArcImsTileProvider : ITileProvider
{
///
/// Private member containing the web service url
///
private string _webServiceUrl = "";
///
/// Constructor that takes a web service Url
///
///
public ArcImsTileProvider(string webServiceUrl)
{
_webServiceUrl = webServiceUrl;
}
///
/// Get the tile image
///
///
///
///
/// Tile data stream
public System.IO.MemoryStream GetTile(ITileExtent extent, int tileHeight, int tileWidth)
{
MemoryStream returnStream = null;
try
{
string axl = getAXL(extent, tileHeight, tileWidth);
Stream responseStream = PostData(_webServiceUrl, axl);
XmlDocument xd = new XmlDocument();
xd.Load(responseStream);
string imgURL = xd.GetElementsByTagName("OUTPUT")[0].Attributes["url"].Value;
responseStream.Close();
Bitmap bm = new Bitmap(new WebClient().OpenRead(imgURL));
returnStream = new MemoryStream();
bm.Save(returnStream, ImageFormat.Png);
}
catch(Exception e)
{
Bitmap bm = GetMessageTile(e.Message);
returnStream = new MemoryStream();
bm.Save(returnStream, ImageFormat.Png);
}
return returnStream;
}
///
/// Gets the ArcIMS GetImage AXL request.
///
///
///
///
/// GetImage ArcIMS AXL request
private string getAXL(ITileExtent extent, int tileHeight, int tileWidth)
{
StringBuilder sb = new StringBuilder();
sb.Append("<?xml version=\"1.0\" encoding=\"UTF-8\" ?>");
sb.Append("<ARCXML version=\"1.1\">");
sb.Append("<REQUEST>");
sb.Append("<GET_IMAGE>");
sb.Append("<PROPERTIES>");
sb.Append("<ENVELOPE minx=\"" + extent.lon2 + "\" miny=\"" + extent.lat2 + "\" maxx=\"" + extent.lon + "\" maxy=\"" + extent.lat + "\" />");
sb.Append("<IMAGESIZE height=\"" + tileHeight + "\" width=\"" + tileWidth + "\" />");
sb.Append("</PROPERTIES>");
sb.Append("</GET_IMAGE>");
sb.Append("</REQUEST>");
sb.Append("</ARCXML>");
return sb.ToString();
}
///
/// Gets a tile with an error message burned into it.
///
/// The message.
/// An error message PNG
private Bitmap GetMessageTile(string message)
{
Bitmap tile = new Bitmap(Properties.Resources.blankTile);
Graphics graphics = Graphics.FromImage(tile);
Font drawFont = new Font("Arial", 12);
SolidBrush drawBrush = new SolidBrush(System.Drawing.Color.Black);
SizeF len = graphics.MeasureString(message, drawFont);
graphics.DrawString(message, drawFont, drawBrush, new PointF(10, 10));
graphics.Dispose();
return tile;
}
///
/// Does an HTTP Post, returning a stream.
///
/// The URL to post to
/// The data to post
/// The Http response stream
private Stream PostData(string sURL, string postData)
{
HttpWebRequest webReq = null;
HttpWebResponse response = null;
Stream requestStream = null;
StreamWriter writer = null;
Stream responseStream = null;
try
{
webReq = (HttpWebRequest)WebRequest.Create(sURL);
webReq.Method = "POST";
webReq.ContentType = "application/x-www-form-urlencoded";
webReq.Timeout = 0xea60;
webReq.AllowAutoRedirect = true;
requestStream = webReq.GetRequestStream();
writer = new StreamWriter(requestStream);
writer.Write(postData);
writer.Flush();
writer.Close();
requestStream.Close();
response = (HttpWebResponse)webReq.GetResponse();
responseStream = ((HttpWebResponse)webReq.GetResponse()).GetResponseStream();
}
finally
{
if (writer != null) writer.Close();
}
return responseStream;
}
}
}
Winners: Python-fearing .NET folks still using ArcIMS. All six of you!
Losers: “ArcGIS Server Virtual Earth Tile Server” as a name. Die.