Leaflet: Lean, Mean Javascript Maps

A few weeks back I tweeted about some fun stuff we were doing with the Leaflet javascript map library. For those who may not know about it, Leaflet is a new(ish) library from Cloudmade (http://leaflet.cloudmade.com/). What’s really great about this library is that is really really lean. Like 24Kb on the wire. Of course this means that instead of handling every possible thing in every browser, the developers focused on a reasonable subset of functionality, and make the assumption you’re using a reasonably modern browser.

How Lean is Lean?

As I said, we’re talkin’ 24Kb total and it’s all in one file, which means one request. This makes it ideal for use in mobile web applications. Compared to the Esri Compact javascript api, which is 114Kb itself, AND makes 11 additional requests for more Dojo pieces and parts, totaling out to ~145Kb, Leaflet is substantially leaner. And since there is less javascript running… it’s also faster.

Leaning on the Browser: CSS3

Another noticeable difference is that Leaflet leans heavily on CSS3. This alone is good because CSS3 operations (transforms etc.) are native so they are MUCH faster than doing the same thing via javascript. And, on iOS, CSS3 transforms are hardware accelerated, which means super smooth panning and zooming. Relying on CSS3 also removes a ton of code – of course if your end users are rocking Internet Explorer 6, this may be sub-optimal. (What isn’t sub-optimal in IE6??). Luckily for us all, the vast majority of smartphones use a webkit browser Winking smile

ArcGIS Server Goodies

Ok, so that’s set the stage – leaflet is good and shiny, but how do we (die-hard Esri geogeeks) integrate services hosted on ArcGIS Server? We write code! (mostly)

Tiled Map Services

Tiled map services are really easy to use in Leaflet and don’t require any coding. Since Leaflet has a TileLayer, and assumes we’re all using the One-True-Projection (did I say there were limitations?) all we need to do is hand the TileLayer constructor the url to the tile service.

var streetMapUrl = 'http://server.arcgisonline.com/ArcGIS/rest/services/World_Street_Map/MapServer/tile/{z}/{y}/{x}';
var streetMapLayer = new L.TileLayer(streetMapUrl, { maxZoom: 19, attribution: 'Tiles: © Esri' });

The thing to note here is that the CloudMade tile urls have the parameters ordered differently ({z}/{x}/{y}) than an ArcGIS Server tile cache ({z}/{y}/{x}). That’s it!

ArcGIS Dynamic Map Services

This does require some code (over in GitHub if you want to peek). I ended up creating two types of layers that use ArcGIS Dynamic map services. The first one I build is based off the ImageOverlay class. The AgsDynamicLayer class takes the url to a map service, and will make requests for map images that cover the visible extent (just like the ArcGISDynamicLayer in the javascript and Flex APIs). You can specify which layers in the map service to show, as well as setup definition queries.

var sitesLayer = new L.AgsDynamicLayer(
    'http://ags2.dtsagile.com/ArcGIS/rest/services/LiveFeeds/WxMappr/MapServer',
    { maxZoom: 19,
        attribution: "NOAA",
        opacity: 1,
        layers: 'show:2' });
_map.addLayer(sitesLayer);

This is a *minimalist* implementation – if you want to use this, and it’s missing a feature you want – add it! Since it’s using the REST API, this is really just about creating Urls, so it’s simple. Also – this example is using a demo NEXRAD service, so don’t use it in your apps. Ok, you actually could and we likely would not notice, but we move stuff around a lot so it will likely break at some really inconvenient time, and then your boss will be all up in your face etc. etc. In short – be cool. Moving on…

Turns out that this works quite well in desktop browsers, but crashes Safari on iOS after a bunch (like 50) pan/zoom operations. Not quite sure why this is, but hopefully someone can take a peek at the code and have an “Ah HA!” moment and fix this.

SO – since that did not work on mobile browsers, and I saw that there was a TileLayer.WMS class in the repo, I thought I’d go that route – assuming that whatever was causing Safari on iOS to puke would not be an issue. Thus the TileLayer.AGSDynamic class (yeah yeah – I just noticed the inconsistent casing). This has the same parameters etc as the AgsDynamic layer, but instead of making a request for a single image covering the current visible extent, it makes a bunch of requests for images that line up with tiles.

var nexrad = new L.TileLayer.AGSDynamic(
            'http://ags2.dtsagile.com/ArcGIS/rest/services/LiveFeeds/WxMappr/MapServer',
                 {  maxZoom: 19,
                    attribution: "NEXRAD",
                    opacity: 0.5,
                    layers: 'show:18',
                    cacheBuster: true });
_map.addLayer(nexrad);

This is cool because now you’ll have consistent urls,  which means you’ll play nice with caching and once an image is loaded your pan/zoom operations don’t have to re-load it. However, the first layer I used this with is a NEXRAD feed that updates every 5 minutes, so I added a cacheBuster property which basically tacks a random number on the back of the request to force new images every time. Down the line I’d probably make another custom layer that has a timer and only changes this random string every 5 minutes. Unfortunately, this layer still causes Safari on iOS to crash (doh!)

Here’s a simple screen grab of leaflet, loaded with the Esri Streetmap tile cache, NEXRAD data coming in via TileLayer.AGSDynamic and windfields coming in via AgsDynamic.

ll-ags

Lets Play!

I’m going to push up some simple demo’s later today (and will update this post) but until then   UPDATE: Live demo’s of can be found at http://demo.dtsagile.com/leaflet

You can fork our Leaflet repo at GitHub or just grab code, and use the agstile.html and ags-dynamic.html files includes in /debug/map. Once we (or someone) sorts out why these are crashing Safari, we’ll submit a pull request and hopefully get this into the main branch of the Leaflet source.

Posted in ArcGIS Server, javascipt, Leaflet | 5 Comments

Mobile Custom View Engine Code

Today I gave a talk at the  Microsoft Special Interest Group about using ASP.NET MVC to serve device specific views. In that talk I used a CustomViewEngine class (code is here)

This code was modified from this post by Scott Hanselman. To use it, use Package Manager and install 51degrees.mobi, comment out the redirect to Mobile/Default in the App_Data/51degrees.mobi.config file, drop in this class, and add the viewengines in Global.asax.cs like so:

ViewEngines.Engines.Clear();
ViewEngines.Engines.AddIELessThan9<RazorViewEngine>();
ViewEngines.Engines.AddBlackBerryLessThan6<RazorViewEngine>();
ViewEngines.Engines.AddWP7<RazorViewEngine>();
ViewEngines.Engines.AddPhone<RazorViewEngine>();
ViewEngines.Engines.AddAndroidPhone<RazorViewEngine>();
ViewEngines.Engines.AddIPad<RazorViewEngine>();

//Everybody else gets the full blown dealio
ViewEngines.Engines.Add(new RazorViewEngine());

Posted in Uncategorized | Leave a comment

Flex Special Interest Group Presentation

Today I gave a really rapid fire presentation at the Flex Special Interest Group at the Esri Users Conference. I showed 11 flex apps in ~5 minutes – so clearly it was a whirlwind. Here are the the links to the public facing sites so you can explore them a little more.

#1 ForestHealth.info – our first flex app / particle graphs

#2 Esri Mashup Entry – particle effects v2

#3 Texas Wildfire Risk – very customized Flex Viewer

#4Utah Historic Buildings – server side clustering

#5 Forest Disturbance Mapper (login required) – thresholding

#6 Exotic Forest Pests Portal – potential distribution tool – PixelBender v1

#7 Esri ChangeMattersViewer App – PixelBender v2

#8 Texas Wildfire COP – Flex Viewer

#9 Fire Intel Viewer – real-time data feeds

#10 DTSWildfire COP R&D – Community Analyst Online integration (login only)

#11 Video Chat Widget for Flex Viewer (login only)

Posted in ArcGIS Server, Esri, Flex | Leave a comment

Esri UC BackChannel: Mobile Agenda & More!

The Esri User Conference is a little less than a month away, and we’ve cooked up another BackChannel web site / mobile web app for everyone to enjoy. To be clear, this is just a site that we built for the fun of it – Esri is not involved (yet!) and thus this is a very “un-official” type of thing.

We streamlined things a little since last year, focusing on the features people found the most useful and fun. Here’s the rundown…

Conference Agenda

We updated the agenda significantly. This year the agenda is a self-contained javascript application that uses local storage to cache the session information.

desktop-agenda

This is important because there are well over 1200 sessions/events at the UC, and making a request for every search / filter operation would be brutally slow over 3G. By loading the data once a day (takes ~20 second on 3G) searching/filtering sessions is lightning fast because everything is already loaded into the browser. The app has two user interfaces – one for desktop & tablet browsers and another for smartphones.

mobile-agenda

In both apps you can select sessions you want to attend, and these settings will be stored between visits – all in local storage in your browser.

If you register and log into the site, the Agenda app will send the sessions you select back to our server and we’ll be able to sync your agenda selections between your desktop browser and your smartphone. We think that this is a really smooth user experience and encourage users to check this out.

For those geeks interested, we used some python goodies to scrape the agenda info directly from Esri’s web site – we run this script daily and it spits out an optimized json file, which is then dumped into the site and gzipped during download. The app will pull this file down once a day. I’ll post more about this some other time.

Session Evaluations

The agenda app also features the ability to submit your session evaluations digitally. When you are in a session, simply look it up on the agenda app, and the “evaluate this session” area will become active.

session-eval

Note: you can only submit evaluations for a session *after* the session has started. To encourage the use of this digital feed-back mechanism, you’ll get 10 points for every session evaluation you submit… and yes we check to make sure you submite no more than 2 per time-slot). And, just so this is clear, we will be sending Esri all the evaluations that are submitted via this application and that information will be anonymous.

Photo Safari

This was by far the most used part of last year’s BackChannel, and it’s back. We’ve dramatically improved how photos get submitted. Instead of having to download the photo to your PC and manually upload it, we’ve integrated the app with both Facebook and Instagram, allowing either to be used as a source for photos.

desktop-upload

This allows uses to take photos with their phones, upload them to Facebook or Instagram and then log into the BackChannel and select a photo from either source.

mobile-upload

Simple as can be, and very easy to do on the go. In addition to a cadre of Esri employees and other sundry geo-nerds, we’ve also added some San Diego landmarks to the Photo Safari, so be sure to check those out.

Recruiting, Points, Shwag and all that Jazz

Last year the app was a lot of fun, and we had just over 200 participants. This year we’d love to get a lot more people involved – and at the same time up the ante (the prizes get better the more people that participate – once we’re over 500 people, we start into the Apple products!) So, we’ve added an easy way for people to start getting ahead now – even before the conference starts!

When you register, you’ll get a personal “recruiting url”. For anyone that registers using that url, you’ll get 20 points (10 when they register, and another 10 when they become “active” which means they have earned 30 points).

my-recruiting-url

So – get over to http://uc.dtsagile.com and register using your Facebook or Twitter account, and then spam all your coworkers & geo-accomplices heading to the UC, and get them to register with your url Winking smile

You’ll also get 20 points for registering, and 10 points for every session evaluation you submit. Of course the points vary for each person / place on the Photo Safari, so you can earn a lot of points that way.

But, what if I’m not going to the UC?

Well, you can follow along in the fun by checking out all the photos (at this time there are only test photos) that have been submitted, or just checking in on the Social Stream page where we harvest various social media streams onto a single page. Post anything on twitter with the #Esri or #EsriUC hash tag and it will get pulled in there as well. As for winning points etc, you’ll be at a major disadvantage if you’re not actually in San Diego!

Why do we do this?

Good question! A few years ago I wrote a blog post about Rethinking Conferences. My main point was that many conferences had become dull. Between “technical” sessions that are thinly veiled marketing speeches by non-technical sales people, to the creeping death of bad presentations, many conferences had lost their spark. Since I don’t run conferences, there’s only so much I personally can do to change the content presented at these events (i.e. make an effort to give energetic, entertaining and educational talks – 1:30pm on Tuesday in Room 29B I’m talking about Deploying ArcGIS to the Cloud), I do have the power to create something that kicks some life back into an event. Thus the BackChannel. While the Esri UC had not “lost it’s spark” per-se, it is HUGE, and if you don’t know a lot of people attending, it’s a pretty overwhelming event. Having something like the BackChannel is kinda like having a built-in posse – people who you know you share something with – even if it’s just trying to get a photo with Jack!

With that, I invite you to jump in, register and start spreading the love. We’ve got a few weeks left before the conference and we have a few more ideas for things we’d like to add, and things we are going to tweak, so stay tuned. I hope to see you all out in San Diego – trying to get a photo with Jack!

Posted in Uncategorized | Leave a comment

Debugging ASP.NET MVC3 Apps using oAuth Secured APIs

We have been working on the 2011 of the un-official Esri User Conference BackChannel app, and one thing we added this year is the option to register and sign-in using your Facebook or Twitter credentials. To be more specific, the app uses the oAuth services from Facebook and Twitter – you do not actually POST your credentials to our site – which is one of the key concepts in oAuth Winking smile

oAuth is a relatively simple little back and forth dance between the user’s browser, your app, and the oAuth provider, involving appId’s, secrets and tokens.

Here’s a diagram showing the basics of how this works (from Facebook).

serversideflow

You can read all the lovely details about how this works on the Facebook developer site and many other locations. Be sure to read the specifics of the API you want to access as not all oAuth’s are created equal.

Really though, this is not too difficult to grok or implement after you play with it a bit. However, there are some tricks to being able to debug or work with an app that uses this on your local machine. In the middle of the diagram you see a line with “302 Redirect including code parameter”. Basically that’s where things get tricky.

When you register an application at Facebook (or Twitter or Instagram), you need to tell the Facebook what your callback url will be – i.e. where the they will redirect the client’s browser to after they have logged into the service and granted your app access to their data.

In our case the callback url will be a controller under http://uc.dtsagile.com – a real internet address. Which begs the question – how can I do development on my local box and not the server, and still have this redirect work correctly?

Basically are two options: hacking your hosts file so that you map that DNS entry to your local machine (works but is problematic at a number of levels) or something much slicker which I found while integrating the instagrammer library written by Chris Jones (jonezy).

In the sample project that’s part of the instagrammer package, Chris did a few interesting things. First, he registered two applications with instagrammer – one setup with a public url as the callback, the second – a debug app, was setup with http://localhost as the callback. This alone is one of those “doh! that’s sooooo obvious once you see it” things.

The slick second thing he did related to managing appsettings in web.config.

  <appSettings>
    <add key="Environment" value="Debug"/>
    <add key="Debug.ClientId"
         value="bfNOTTHEREALID5e"/>
    <add key="Debug.ClientSecret"
         value="5ccNOTTHEREADSECRET9"/>
    <add key="Debug.CallBackUrl"
         value="http://localhost/Instagrammer/OAuth/AccessRequest/"/>

    <add key="Release.ClientId"
         value="aNOTTHEREALIDc0"/>
    <add key="Release.ClientSecret"
         value="5NOTTHEREALSECRET7"/>
    <add key="Release.CallBackUrl"
         value="http://instagrammer.jonezy.org/OAuth/AccessRequest/"/>
  </appSettings>

As I mentioned oAuth uses a client Id (the id of the application that you setup at the service) and the Client Secret (the code provided by the service that only your app knows). We can see both the debug and release Ids,  Secrets and urls. The cool trick here is that he prefixes the key with “Debug” and “Release” and sets the value to use in the Environment setting. Now, normally to get the value from an appsetting we do something like:

_applicationId = ConfigurationManager.AppSettings["facebookAppId"];

but now that we have our key’s prefixed, you’d actually need this:

_applicationId = ConfigurationManager.AppSettings["Debug.facebookAppId"];

And while this would work, running all around your app changing from Debug to Release every time you publish the app would be tedious. So there is a hand helper to hide the details…

_applicationId = EnvironmentHelpers.GetConfigValue("faceBookAppId");

This helper simply looks up the value of the Environment appsetting, and tacks it on the front of the values passed in, and then uses ConfigurationManager as usual.

public static class EnvironmentHelpers
{
    public static string GetConfigValue(string partialKey)
    {
        string fullKey = string.Format("{0}.{1}",
            ConfigurationManager.AppSettings["Environment"].ToString(),
            partialKey);
        return ConfigurationManager.AppSettings[fullKey].ToString();
    }
}

Streamlining Deployment

Of course you are using WebDeploy to push your apps from your dev box (or build system) over to your production IIS server. In which case you already know about using the Xml transforms in your web.config.debug and web.config.release files… like this

<configuration xmlns:xdt="http://schemas.microsoft.com/XML-Document-Transform">
  <connectionStrings>
    <add name="UCBackChannel"
      connectionString="YOUR CN STRING"
      xdt:Transform="SetAttributes"
      xdt:Locator="Match(name)"/>
  </connectionStrings>
  <appSettings>
    <add key="Environment" value="Release"
         xdt:Transform="SetAttributes"
         xdt:Locator="Match(key)"/>
  </appSettings>
</configuration>

In case you don’t, this transform will be applied during a webdeploy deployment, and in this case, it does two things – changes the connection string to point at the production database server, and two it changes that Environment appsetting to point at release. While not capistrano, these transforms combined with WebDeploy make deployments much much better.

Caveats

Creating a second “debug” application with a localhost callback works well at Facebook and Instagram. Twitter is wise to “localhost” and correctly senses that it’s not a valid callback out in the “wild”. However, it can be tricked if you use 127.0.0.1 (the loopback alias for the local machine. Keep in mind that this does complicate things though, especially when you try to use multiple services together – where some use “localhost” in the callback and others use 127.0.0.1 – has to do with cookies in your browser etc.

Summary

Using oAuth is a powerful way to allow your users to access your site’s services without having them create “yet-another-account”. After you get past the initial “wtf is going on” with oAuth, using the tactics described here can help streamline your development.

Posted in asp.net mvc, C#, Esri, oAuth | Leave a comment

ASP.NET MVC3 Google Analytics Html Helper

While we do a lot of different types of projects, almost all of them boil down to creating a web site or app. And almost everyone wants to know usage information about the site/app, and almost everyone uses Google Analytics.

For the most part, adding Google Analytics is just a matter of dropping some javascript into the layout for the site, but that’s not always a single file. More frequently we finding ourselves building custom views for desktop, tablet and smart-phone. And while the “web-site” design community is preaching all about responsive design and fluid grids, the simple fact is that for actual “web apps”, you’re WAY better off building an interface that’s specific to the form factor / device. Anyhow, this long rambling intro led me to a problem – in these apps with multiple views, we end up having the Analytics code in multiple locations, thus making changes to the Analytics somewhat painful.

So, I built a simple Html helper.

<!DOCTYPE html>
<html>
<head>
   <title>@ViewBag.Title</title>
</head>
<body>
    <div>
         @RenderBody()
    </div>
     @Html.Analytics("UA-22787686-6","dtsagile.com")
</body>
</html>

The Analytics method takes the urchin code, and the domain name. As you can see in the code below, it also has a overload that takes no arguments, and simply pulls the values from AppSettings.

  <appSettings>
    <add key="ga-urchin" value="UA-22787686-6"/>
    <add key="ga-domainName" value="dtsagile.com"/>
  </appSettings>

The helper itself is completely simple… and just uses a string builder to build up the analytics javascript.

using System.Configuration;
using System.Text;

namespace System.Web.Mvc {
    public static partial class HtmlHelpers
    {
        /// <summary>
        /// Insert GA with an Urchin and domain name
        /// </summary>
        /// <param name="htmlHelper"></param>
        /// <param name="urchin"></param>
        /// <param name="domainName"></param>
        /// <returns></returns>
        public static HtmlString Analytics(this HtmlHelper htmlHelper, string urchin, string domainName)
        {
            StringBuilder sb = new StringBuilder();

            sb.Append("<script type='text/javascript'>");
            sb.Append("  var _gaq = _gaq || [];");
            sb.Append(" _gaq.push(['_setAccount', '" + urchin + "']);");
            sb.Append(" _gaq.push(['_setDomainName', '" + domainName + "']);");
            sb.Append(" _gaq.push(['_trackPageview']);");
            sb.Append("  (function() {");
            sb.Append("   var ga = document.createElement('script'); ga.type = 'text/javascript'; ga.async = true;");
            sb.Append("    ga.src = ('https:' == document.location.protocol ? 'https://ssl' : 'http://www') + '.google-analytics.com/ga.js';");
            sb.Append("   var s = document.getElementsByTagName('script')[0]; s.parentNode.insertBefore(ga, s);");
            sb.Append("  })();");
            sb.Append("</script>");

            return new HtmlString(sb.ToString());
        }

        /// <summary>
        /// Pull the urchin and domain name from Web.Config
        /// </summary>
        /// <param name="htmlHelper"></param>
        /// <returns></returns>
        public static HtmlString Analytics(this HtmlHelper htmlHelper)
        {
            //pull values from Config
            string urchin = ConfigurationManager.AppSettings["ga-urchin"];
            string domainName = ConfigurationManager.AppSettings["ga-domainName"];
            return Analytics(htmlHelper, urchin, domainName);
        }
    }
}
 

Have fun!

Posted in Uncategorized | 3 Comments

ChangeMatters: Behind the Scenes

Yesterday, Jack Dangermond announced the public launch of the Esri Landsat Image Services, and the ChangeMatters applications. Over time, I think that the community at large will find the image services to be really powerful and a great help in examining change over time. In the near term, the ChangeMatters applications are the public face of the services. Working with Esri, in conjunction with Kass Green and Associates, DTSAgile designed and built the applications, so I thought I’d share a little about how the apps were designed and some of the less obvious features.

Meet the Apps: “Compare” and “Explore”

There are actually two apps that make up the ChangeMatters site. The compare app lets you view two years side by side, along with the NDVI Change between those two years. This is a high impact, visual comparison application, and thus is the “gateway” application.

image

 

There is a second, more analytical application – “Explore” that presents additional functionality in a single map view. You can get to this application by clicking on the “Full Screen” link in the compare app, or by visiting this url http://changematters.esri.com/explore

image

This application allows users to get more information about the image maps they are viewing (in this case,  “Healthy Vegetation” aka a “4-5-1” in Remote Sensing Speak), as well as so some on-the-fly histogram based change mapping.

image

This client-side histogram slicing required the use of PixelBender (My “Getting Flexy With It” talk at DevSummit covers this as well), and thus the Explore app is a Flex application.

 

Multiple Clients, Multiple Applications

Early on it was decided that the ChangeMatters applications would need to run on both desktop systems and tablets. And since the iPad is the most dominant tablet on the market, this meant that we needed to have javascript versions of the applications. More than just writing the apps in javascript, we needed to make sure that they were “touch” friendly, and that the right version was served to the right client.

Since the “Compare” application was written in javascript from the beginning, tweaking it for a smaller, touch based experience was relatively straight-forward. Mike Juniper, one of our Javascript wizards, has a few posts about subtle tweaks needed to make things work smoothly for iPad and the Motorola Xoom. However, Internet Explorer did pose an issue.

Having 3 Javascript API map canvases in a single page involves a LOT of javascript. It works just fine in Chrome, Firefox, and Safari, Mobile Safari and the Android browser, but the javascript performance in Internet Explorer 7 & 8 is so bad that we ended up creating a flex version to ensure that all users had a good experience.

image

 

As I already noted, the Explore app was designed to have the histogram slicing, and thus was created in Flex. In addition to the obvious issues of Flex not running on an iOS device, the interface had to be re-designed the interface so that it was “finger friendly”. This is a key idea – when using a mouse, your “click targets” can be pretty small – a 10px square is easy to hit with a mouse, but very difficult to hit with a 40px by 40px “finger”.  Here’s a scree shot of the tablet version. image

One very handy tool we used during development was the User Agent Switcher add-on for Firefox.

I talked about this in my HTML5 talk at the Developer summit, but the site uses ASP.NET MVC as the backend, and we used a custom view engine to serve different “views” to the different devices. I’ll post more about this in the future.

Sharing a View: Deep Linking

Another goal of the project was to allow people to jump between the applications, as well as have the ability to “share” a particular view, and this required building out a “deep-linking” capability. At it’s core, this is pretty simple – just encode the center point,  zoom level, visible layers and time extent into a url, and allow users to share that. Here’s one of those urls http://changematters.esri.com/explore?level=12&center=-8429925.591874605,5674329.685858726&im=HealthyVegetation&yr=2005

Having multiple versions of the application and ensuring that a user running the Flex version of Compare in IE8 can share a url with someone using an iPad was something of a challenge in terms of keeping all the parameter names the same. Once we had the deep-linking working, we integrated the option to share the view via FaceBook or on Twitter.

image

Telling a Story with a Tour

Having a global archive of multi-temporal Landsat data really provides an exciting platform for telling stories of change – since we had the deep-linking capabilities built into the applications, we were able to use the underlying code that zooms the map to a location, change the image maps, and sets the time extent, and extend it to take users to different locations in the form of a guided tour.

image

To build this out, we created another simple application that allowed Kass Green as well as some Esri staff to create the tour’s, directly in a browser.

image

The tour editor was built in a few hours by leveraging both Entity Framework Code-First to create the underlying database and repository directly from the domain models and MVCScaffolding to create some basic CRUD interfaces. Once that was done, we dropped in an Esri Javascript API map, wired up the “Set Location” and Preview Pop-up buttons and it was ready to roll. Here are a few of the tours:

Change Matters Tips – information about the image services, things to look out for in the imagery

Dubai – talk about a place that went through massive change

Mount St. Helens – Having the Infrared data prior to the eruption in 1982, we can really see the effects of the eruption and the regrowth since then

For those interested, Steve Sanderson (Microsoft) did a presentation called  Scaffolding – ASP.NET, NuGet, Entity Framework Code First and More at MIX11

Summary and Additional Resources

Having been in the geo industry for some 15 years now, it’s amazing to think about these services – global Landsat data, for multiple time periods, available for use in web applications and in your desktop GIS systems, for free. I have already talked to a number of our clients who will be leveraging these amazing image services in their workflows, and I’d really recommend checking them our yourself. If you see Jack Dangermond, say “Thanks!”

I also wanted to mention that Jeff Germain, our lead Flex developer, wrote up a blog post about consuming these services in the Flex API, and specifically how to use the MosaicRule to ensure that the image stacking order is always optimal. I’d also note that you really need to use the very latest and greatest version of the Flex API when you are using the Mosaic Rule stuff Winking smile

Overall, this was a super fun project, and we are really pleased with the released version. Thanks to the team at Esri, and Kass Green for involving us in the project, and allowing us to blog about it.

| 2 Comments