# Friday, June 03, 2011

A colleague showed me an interesting problem, the ASP:LinkButton controls in our ASP.Net 4.0 website wouldn't work when it was viewed from a browser control hosted inside an iOS app (ie. The viewer that pops up in the Facebook app when you click on a weblink) What made it weirder was that depending on the order you hit the webpage, either through the Facebook App first, then through Safari. The link button might or might not work.

We ran some test on an ASP.Net 2.0/3.5 site, and the LinkButtons on those sites worked fine. Baffled, I enabled trace.axd on the server to see if there were any differences between requesting for a page through the Facebook App, and through Safari. Immediately I noticed that the User Agent string was different.

When viewed through Safari the User Agent string was something like this.

Mozilla/5.0 (iPhone; U; CPU iPhone OS 4_3_2 like Mac OS X; en-us) AppleWebKit/533.17.9 (KHTML, like Gecko) Version/5.0.2 Mobile/8H7 Safari/6533.18.5

When the page was viewed through an app the User Agent looked like this.

Mozilla/5.0 (iPhone; U; CPU iPhone OS 4_3_2 like Mac OS X; en-us) AppleWebKit/533.17.9 (KHTML, like Gecko) Mobile/8H7

Notice that both the Version and Safari values are missing when viewed from the app.

In order to figure out what the difference was when these 2 values are missing, I fed the 2 UserAgent strings through IE9's developer toolbar and viewed the page on the desktop so I had more debugging ability. And to my surprise, when I used the UserAgent string without the Safari moniker, the following code was missing from the output page.

function __doPostBack(eventTarget, eventArgument) {
    if (!theForm.onsubmit || (theForm.onsubmit() != false)) {
        theForm.__EVENTTARGET.value = eventTarget;
        theForm.__EVENTARGUMENT.value = eventArgument;
        theForm.submit();
    }
}

This happens to be the Javascript code which ASP.Net LinkButtons and various other auto postback controls will use to post the form through script on the page. So if the function was missing, then none of the controls would be able to post anything. So I begun my search on why the code was missing when the Safari moniker is missing. And I found the source of the problem, ASP.Net's feature for dynamically changing the way something is rendered based on the client's browser capability. Based on the sample shown on this page on how to see what browser capability was detected, I wrote a quick page which dumps the browser capabilities out with the code below.

        Dim ht As IDictionaryEnumerator = Request.Browser.Capabilities.GetEnumerator
        Response.Write(Request.Browser.Id)
        Response.Write("<br/>")
        Response.Write(Request.UserAgent)
        Response.Write("<br/>")
        Response.Write("----------------<br/>")
        While ht.MoveNext = True
           
            'If ht.MoveNext() = True Then
               
            Response.Write(String.Format("{0}:{1}", ht.Key, ht.Value))
            Response.Write("<br/>" & vbCrLf)
           ' End If
        End While

That's when I realized that WITHOUT the Safari moniker, the default browser capability DISABLES JAVASCRIPT that's why the clientside postback chunk was not delivered to the server.

Interestingly enough even without the Safari moniker, an ASP.Net 2.0 site will still flag the iPhone browser as Javascript capable.

Now that I knew what was missing, what was left was to make a new Browser Definition File which will enable Javascript for the ASP.Net 4.0 site even without the Safari moniker. I basically copied the definition for the Safari browser, but made it so it'll look for the AppleWebKit moniker in the UserAgent instead of the Safari moniker and flag it as Javascript capable.

<browsers>
  <browser id="safariiphone" parentID="mozilla">
    <identification>
      <userAgent match="AppleWebKit"/>   
    </identification>
    <capabilities>
            <capability name="version"                         value="${version}" />
            <capability name="majorversion"                    value="${major}" />
            <capability name="minorversion"                    value="${minor}" />
            <capability name="type"                            value="Safari${major}" />
            <capability name="ecmascriptversion"               value="3.0" />
            <capability name="javascript"                      value="true" />
            <capability name="javascriptversion"               value="1.6" />
            <capability name="w3cdomversion"                   value="1.0" />
            <capability name="tagwriter"                       value="System.Web.UI.HtmlTextWriter" />
            <capability name="cookies"                         value="true" />
            <capability name="frames"                          value="true" />
            <capability name="javaapplets"                     value="true" />
            <capability name="supportsAccesskeyAttribute"      value="true" />
            <capability name="supportsCallback"                value="true" />
            <capability name="supportsDivNoWrap"               value="false" />
            <capability name="supportsFileUpload"              value="true" />
            <capability name="supportsMaintainScrollPositionOnPostback" value="true" />
            <capability name="supportsMultilineTextBoxDisplay" value="true" />
            <capability name="supportsXmlHttp"                 value="true" />
            <capability name="tables"                          value="true" />
        </capabilities>
  </browser>
</browsers>

This file is saved as whateveryouwant.browser then placed under the App_Browsers folder of the website so it can be processed by ASP.Net. This fixed my problem but I was still still curious as to why it worked in ASP.Net 2.0 but NOT 4.0, so I dug around the Browser Definition Files for ASP.Net 2.0 and found this element it used to identify the Safari browser in ASP.Net 2.0

        <identification>
            <userAgent match="AppleWebKit/(?'webversion'\d+)" />
        </identification>

Which means that in ASP.Net 2.0 it's looking for the AppleWebKit moniker to identify Safari browsers, where as in ASP.Net 4.0 the identification element reads this.

        <identification>
            <userAgent match="Safari" />
            <userAgent nonMatch="Chrome" />
        </identification>

Seems like it was trying to avoid clashing with Google Chrome's Useragent which also happens to contain the AppleWebKit moniker but they ended causing problems in certain scenarios.


Friday, June 03, 2011 6:03:28 PM (Malay Peninsula Standard Time, UTC+08:00)  #    Comments [2]  | 
# Tuesday, May 24, 2011

Well, I finally managed to release my first Windows Phone 7 game on the Marketplace, the Bullet Hell Simulator. While I rushed and put the thing on Marketplace BEFORE I had properly finished it and would most likely suffer for it, let's take a look at the evolution of the idea.

First there was the concept of shooting lots of stuff that randomly popped on screen.

Then after much background work, the core engine came up which allowed the creation of sprites that were controlled using an XML markup script.

Then finally.. version 1.0 of the program. Which was quite a mess because of the rambutan shaped enemy bullets, the fact that I accidentally DOUBLED the enemy bullet hit radius. Difficulty levels that didn't change the difficulty much, you couldn't actually die or be notified that your performance sucked, etc. etc.

And now... version 1.1 with shield blast gimmick, some enemy tweaks and balancing, difficulty levels that actually make the game easier on easy.

I wonder if I'll find time to document my XML based movement script? :P


Tuesday, May 24, 2011 12:19:03 AM (Malay Peninsula Standard Time, UTC+08:00)  #    Comments [5]  | 
# Wednesday, April 27, 2011

I never thought I would get a Razer product since they make mostly mice for PC game players, and I've pretty much swore off PC games. So boy was I surprised when I found myself picking up the Razer Onza Tournament Edition Xbox 360 Controller

DSC00749

When you first unpack it out of it's classy looking box and hold it in your hands, it feels incredibly light! Which coupled with the rubber like surface makes it feels incredibly cheap since there's no sense of mass, at first I thought they didn't include the rumble motors inside but after playing a bit it confirmed that yes, the stick rumbles. So if you don't like your joypads light you might want to stick some weight on this.

Another interesting problem is that the top left and right corners are SHARP AND POINTY!!

DSC00755

Why the heck did they make it like that?!?!?! It HURTS if you scrape or press your finger on this, I'm gonna introduce it to a file after this can't have WZ cutting himself on it when I leave it in the room.

Let's talk about the pad's nifty features now, first we start with the face buttons.

DSC00755

We can't really call these buttons, they are basically little caps sitting directly on top of the switches. They have very little travel distance, which means when you press these they engage almost immediately. How much difference does this make in a match already running with lag through the internet is anybody's guess but one thing to note is that you need to get used to the fact that you might not even notice you've pressed the button. Also.. the buttons light up because that's the cool thing to do. :P

Next we come up to the D-Pad...

DSC00754

Or rather, the OTHER face button set. Because it's NOT a pad or meant to act like a directional input in the traditional sense, it is just 4 DISTINCT buttons arranged in a cross manner. Absolutely FANTASTIC for use in games where you use the D-Pad to select weapons cause you know exactly which direction you're pressing. Pretty much USELESS if you're thinking of using it for fighting games and such. Oh and these are normal buttons which have travel distance and not like the hyper-response (Razer's name) ABXY buttons.

The Onza TE's headphone jack

DSC00764

Is in the usual spot at the button of the controller, note that it will not accept the puck style connector. And I've personally haven't been able to test it out properly yet cause on some reviews they mentioned that there's interference using this port.

Then we have the shoulder buttons

DSC00772

Your eyes do not decieve you, there are TWO bumper buttons. The lower one is your regular LB RB button, the higher one is called the Multi Function Button (MFB) and is one of the main selling point for this controller. Through the use of the assign buttons below the controller.

DSC00775

You can map the MFB to almost any other button on the pad, with exceptions being that the thumb stick, bumper and trigger buttons can only be remaped to an MFB on the same side. This opens up a world of possibilities, for example in Halo:Reach I can assign the Left MFB to Crouch, and the Right MFB to Jump. This means I can now move and crouch easier since I don't have to hold the left thumbstick down to crouch, and because I don't have to move my finger away from the right thumbstick when jumping some interesting possibilities beckons!

There's just one problem with the whole MFB concept though, and I already knew it when I saw the placement of the button. You also should have figured it out by now. Yes... you're VERY VERY VERY VERY VERY likely to press the wrong button in the heat of a match, it'll most likely go away once you're used to it but if you see me in Reach and I melee and jump at the same time? I'm still not used to it then!

And now for the main reason I decided to buy the Onza, the thumbsticks.

DSC00762

If you're asking yourself what are the little groves underneath the pad, then you're focusing on the right item. The groves allow you to push the housing of the stick downwards. What this achieves is that it makes the stick STIFF and you can in theory make smaller, tighter movements such as when trying to no scope someone. When fully screwed it the stick looks like this.

DSC00763

The problem here is that it's like a screw and as you tighten it it gets harder to turn with each click. What's the problem then? The problem would be when you ask yourself "I'd like this to be a wheee bee tighter, but is it at max yet?" But.. there's no indication of where MAX is, and there's the warning in the manual that states Over tightening the stick WILL damage it so that kind of scares you a bit.

Does a tighter stick give you better control? I haven't played enough games with it to confidently say so. I think it makes some difference though. Not sure wheter it's a good or bad difference.

The Onza has one last trick, and it's a very interesting one. You can swap the sensitivity of the stick from normal to RIDICULOUSLY sensitive while the steps below.

What does this achieve? I can only answer in Halo : Reach terms, a sensitivity of 3 in Reach now acts like a sensitivity of 6. Does that help? Maybe... Would it be considered an unfair advantage? HARD to say. :P

In closing I still can't confidently say wheter the Onza TE will improve your game or not, the button remap and stick sensitivity features are interesting tools to have. But like all tools it's up to the user to learn to use them effectively. I can say it's worth a try if you are a serious FPS player and can spare the price. Because the weird out D-Pad does NOT help at all with any other type of games.


Wednesday, April 27, 2011 11:21:49 AM (Malay Peninsula Standard Time, UTC+08:00)  #    Comments [0]  | 
# Saturday, April 23, 2011

A leaflet for the TURN OFF WEEK (wait... who the heck names a site kkk.org.my?!?!?) was given to WZ, its wants families to turn off their screens and do other things in order to bond and stuff. What I find funny is the list of things they mention you can do during this turn off week. (Zoom.It picture below so you can pan around and read the large brochure)

While some of these are ok, some contradict the aim of turning off the screen. ie.

  • Take family photo - Given that most cameras are digital now, wouldn't you end up having to use a screen to view this?
  • Write a letter to a friend or relative - Through snail mail just for the heck of it?
  • Get out the family photo album, Research your family history - But it's turn off week, so... you want to do said research without the Internet?
  • Teach people computer skills - So it's OK to use the screen when you're not using it?

Some are a bit crazy

  • Paint a picture, a mural or a room - The first 2 are reasonable, But painting a room for the heck of it?
  • Listen to the radio - So... huddling around a TV is bad but huddling around a radio is good?
  • Anything that involves outdoor activities - I'm guessing the aim of the list is "You can do X instead of watching TV" but when X are things like cycling, swimming, climb a hill. I'm sorry, how can that be done on a daily basis. So.. I come back from work at night, instead of playing games with WZ I take him swimming around 8PM? How is that appropriate?

I applaud the aim of trying to foster more family bonding, but telling people to turn off their screens when screens are part of the daily ritual? That's pretty much impossible.

Which is why I'll be giving back the activity form with a giant "Not Participating" written over it.


Saturday, April 23, 2011 12:09:53 AM (Malay Peninsula Standard Time, UTC+08:00)  #    Comments [0]  | 
# Monday, April 18, 2011

The latest release of Microsoft Image Composite Editor has a very neat feature, it can stitch up panoramas by using a video instead of just pictures. Makes it pretty easy to make a panorama like this.

You can also choose specific parts of the video to include in the stitch which allows you to make some surprising effects like this. (Zoom It picture below)

I'm sure you all agree that it's a neat trick!


Monday, April 18, 2011 5:09:35 PM (Malay Peninsula Standard Time, UTC+08:00)  #    Comments [0]  |