Navigation Sample For Windows 8 Metro Style Apps Using .NET

September 22 2011

Doing navigation in Windows 8 apps is a little confusing and not well documented. With that in mind, I put together a sample which should help clarify things.

Joe Stegman outlines the basics in this forum response but let me drill in a bit. The confusing bit is that the templates in VS make your pages use UserControl as the root instead of Page.  So, you have to manually change the root element to Page.  The other confusing bit is that you need to handle things in the OnNavigatedTo override. That's how you can get the NavigationEventArgs and get at parameters that you've passed.

Beware of putting any logic into the Page_Loaded event when using Navigation. I hit a really weird bug where my i/o calls were mysteriously failing when I tried to do them in the Loaded event after I'd committed to the Page navigation paradigm. 

NavigationSample.zip (114.02 kb)

Adding References To System Libraries In Windows 8

September 21 2011

I've been starting to hack on Windows 8 a bit, using C# and XAML and the .NET 4.5 Framework. Y'all will probably figure this out, but if you don't, here's the deal: when you go to add references to system libraries, none of your favorites (System.Web, System.Net, System.Security, PresentationCore, etc.) will show up.  You have to manually browse to C:\Program Files (x86)\Reference Assemblies\Microsoft\Framework\.NETFramework\v4.5 and walla, there they all are in their .NET glory. Party on.

Or not.  Didn’t realize this could get you in trouble when you go to submit.  Look here for the libraries available to you: http://msdn.microsoft.com/en-us/library/windows/apps/br230232%28v=VS.85%29.aspx 

Beware though: .NET in Windows 8 is not exactly .NET.  This reference page starts to explain http://msdn.microsoft.com/en-us/library/windows/apps/br230302(v=VS.85).aspx and this presentation http://channel9.msdn.com/Events/BUILD/BUILD2011/TOOL-930C by the eminent Krzysztof Cwalina definitely helps. 

More coming...

Table Storage, Continuation Tokens, Windows Azure

September 8 2011

By default, queries to table storage will return a maximum of 1000 rows, whether you are using the REST APIs or the LINQ provider.  If you want more rows, you need to get fancy.

It’s pretty easy.  Let’s say you have created some data access classes similar to how the Azure Hands On Labs and samples encourage you to do so. 

So say you’ve got a class that inherits from TableServiceContext that looks like this:

class RawDataContext : TableServiceContext { public RawDataContext (string baseAddress, StorageCredentials credentials) : base (baseAddress,credentials) { } public IQueryable<RawEntity> RawEntity { get { return this.CreateQuery<RawEntity>("RawEntity"); } } }

Well, you are going to want to change that, so your data context returns a CloudTableQuery instead.  So, now, your class should look like this:

class RawDataContext : TableServiceContext { public RawDataContext (string baseAddress, StorageCredentials credentials) : base (baseAddress,credentials) { } public CloudTableQuery<RawEntity> RawEntity { get { return this.CreateQuery<RawEntity>("RawEntity").AsTableServiceQuery(); } } }
Notice how the CreateQuery method has been appended with the AsTableServiceQuery() extension method. Notice also that the return type is CloudTableQuery instead of IQueryable.

But that’s not all. You’ll also need to make some changes when you issue your queries.  So, for example, say you have a DataSource class with a select query that looks like this:

public class RawDataSource { private static CloudStorageAccount storageAccount; private RawDataContext context; public RawDataSource() { storageAccount = CloudStorageAccount.FromConfigurationSetting("StorageConnection"); this.context = new RawDataContext(storageAccount.TableEndpoint.AbsoluteUri, storageAccount.Credentials); } public List<RawEntity> Select(string site) { var results = (from g in this.context.RawEntity where g.PartitionKey == site select g).ToList(); return results; } }

You’ll need to change that query such that it issues the Execute method off the CloudTableQuery result, like this:

public List<RawEntity> Select(string site) { var results = (from g in this.context.RawEntity.Execute() where g.PartitionKey == site select g).ToList(); return results; }

By adding the Execute method, the query will issue the continuation token on your behalf to Azure and concatenate the data to the result set, returning > 1000 rows.

Default Username and Password For A Cisco Router G Broadband Router WRT54G Firmware Version: v2.02.7

September 1 2011

If you are trying to connect to your Cisco Router G Broadband WRT54G, you’ve got to hit http://192.168.1.1 in your browser. You could hit it from this post even.  So that’ll take you to the UI, but first you’ll be prompted by a password.  If you never changed the defaults, they are:

Username: admin

Password: admin

 

That’s  for Cisco Router G Broadband Router WRT54G Firmware Version: v2.02.7.

Then, once you are in, you can change things like the security key., etc.

MVC3 and Windows Azure Tools 1.4 -- Better But Still Messed Up

August 24 2011

Getting MV3 on to Azure used to be really painful. The new Windows Azure Tools 1.4 make things better, but they are still a bit bungled up.  The tools fix the missing assemblies problem (although I still maintain that this shouldn't even be an issue and IT should have them installed on the servers, but that's another issue) in that if you create a new Azure project and choose ASP.NET MVC 3 Web Role, it will set all the assemblies you need to 'copy local.' Thanks guys. 

But, you're still going to have problems deploying to Azure, even you pick the empty template.  Your web.config will be full of things that can trip you up, the most egregious being a default session provider, which points to SQL Express, which no instance of Azure will ever have.  So, if you deploy without fixing that, you're screwed. Additionally, if you use the other providers that are in the web.config, you'll need to tweak them, as they rely on providers that Azure doesn't support.  

I'm calling out the folks who built these tools: this is sloppy. If you really want the gory details on this, you can read more Nathan Trotten's post.

While I'm ranting, if I choose an 'empty web template', why are 20 javascripts included with the project? This happens both with Azure MVC3 projects as well as non-Azure MV3 projects.  Empty means empty.

Oh, one other thing: if you create an MVC3 project not from the Azure Tools and then attempt to deploy it to Azure, you'll run into the missing assemblies problem.  Your life gets a little better if you have SP1 installed because you can invoke the Add Deployable Assemblies feature (explained here), but if you don't have SP1 installed, you'll have to do it manually.

Rudy Rucker on Programming and Communing With The Muse

August 17 2011

From a recent interview by Rudy Rucker:

Some textbooks make it sound as if software engineering is a formal process of making out lists of specifications, milestones, and the like, the process is also an experiential hands-on endeavor. You don’t ride a bicycle by making out lists of part numbers. You have to get on it and lurch around.

There are any number of ways to be creative in CS. In terms of theory, you might come up with a new higher-level way of thinking about computations. In terms of practice, deciding what kinds of programs to create can be creative. Much creativity (and low cunning) comes into play in finding ways to make one’s programs run faster. And designing a program’s interface is an artful process as well.

Just as is the case for writers and painters, programmers will often find that their projects are mutating while they work on them. Certain pathways close up, and newer opportunities emerge. At some point it can feel as everything you see all day long is in some way part of the creative process—as if everything is helping you to get the project done. This is known as communing with the Muse. And, make no mistake, there is a Muse of programming as well as there are Muses of writing and painting.

I'm currently reading Jim and the Flims and, as usual, find myself caught up in the bizarre logic of Rudy's imagination. Highly recommended.

How To Suppress The Gravatar Default Icon

August 4 2011

Gravatar is a nifty service. But if someone on your site doesn’t have a Gravatar, Gravatar will display a default icon.  You have some choices in what gets displayed (documented here), but what if you want nothing displayed?  Well, you can have Gravatar return you a 404, but you need to handle that 404 somehow. Not a big deal, but here’s how I did it.

First off, I started by using this code, which is an ASP.NET control that encapsulates all the Gravatar logic. Then, I mucked around with the override of Render, adding the following:

if (!string.IsNullOrEmpty(DefaultImage))
{
    imageUrl += "&default=404"; // +HttpUtility.UrlEncode(DefaultImage);
}
using (WebClient client = new WebClient())
{
    try
    {
        client.DownloadData(imageUrl);

    }
    catch (WebException webException)
    {
        noImage = true;
    }

}



if (noImage)
{
return;

}

Yes, it means I have to make a call to Gravatar in order to determine to not provide an image, but it is worth it. If performance is an issue, an optimization would be to cache the emails that have already been checked. In fact, I’ll probably add that.  No more default gravatars!

DebuggerNonUserCodeAttribute Saves The Day

July 14 2011

Sometimes Visual Studio is too smart. Hit a situation yesterday where I has a solution with an .exe and a .dll. In the .dll, there's a method called by the .exe that throws an exception.  I needed to test the logic of how the .exe handled that exception. But, while debugging, the project would always break on the throw in the .dll and I couldn't ever get it to continue on to test my logic in the .exe. 

Finally, I got it to bypass the class in the .dll by attibuting the class dll with the DebuggerNonUserCodeAttribute.  Walla! Now I could check the logic in the .exe when the exception was thrown.

MVC3 and Azure -- Back To Classic Dev Versus IT

June 13 2011

Ugh, the evil "Instance 0 of role is initializing" when deploying to Azure. Turns out MVC3 isn't installed on the Azure VMs.  The issue is the same as getting PHP installed into Azure: the Azure virtual machines don't have MVC3 installed by default, so it is up to you to get it on the box. Beware -- just changing the references to MVC3 in your project to "Copy Local" = true will not do the trick, as the MVC references rely on additional assemblies.  So, you have to manually add these assemblies:

  • Microsoft.Web.Infrastructure
  • System.Web.Helpers
  • System.Web.Mvc
  • System.Web.Razor
  • System.Web.WebPages
  • System.Web.WebPages.Deployment
  • System.Web.WebPages.Razor

Which can be found in the C:\Program Files\Microsoft ASP.NET\ASP.NET Web Pages\v1.0\Assemblies\ directory.

The other options are to use the WebPI command line tool to install MVC for you, which is the same idea as my PHP deployment solution.  O, you can send up the MVC installer with your website.  I'm not too keen on that solution, as it means deploying an additional 18MB with each deployment.

Steve Marx goes into all of this more in this post.

I don't get why they can't provision the Azure VMs with the latest/greatest shipping Microsoft runtimes and assemblies to avoid this problem, just as I think the Azure VMs should be provisioned with PHP by default.  That's what you can expect from the top tier ISPs so why not Azure? I suppose the counter argument is that the VMs get bloated with runtimes that aren't used. But the cost is only disk space. Really, I think it comes down to classic IT vs. Dev conflict. I expect IT to have boxes provisioned; that's their job.  But Azure makes it my job as a developer.  And they probably think the exact opposite.

JSON-P and MVC

June 1 2011

Supporting JSON-P with MVC is easy. Just derive a class from ActionResult, like this:

public class JsonpResult : ActionResult { public string Callback { get; set; } public string Content { get; set; } public override void ExecuteResult(ControllerContext context) { context.HttpContext.Response.ContentType = &quot;application/json&quot;; if (this.Callback != null) { context.HttpContext.Response.Write(string.Format(&quot;{0}({1})&quot;, this.Callback, this.Content)); } else { context.HttpContext.Response.Write(this.Content); } } }

Then, in your controller, do the following, assuming you are looking for a querystring called callback (the json-p) convention as a method parameter to your action, and assuming that you have a string of json to send back, return this:

if (callback != null) return new JsonpResult { Content = json, Callback = callback};

Note that I'm not having MVC handle serialization of my objects to JSON. I'm doing that all myself using the JSON classes from Microsoft.Serialization.Json from this project: http://wcf.codeplex.com/

VSAchievements
Visual Studio Achievements
Karsten Januszewski (207 Points)