We have an iPad installed in a demonstration area at our company that allows us to control a few items in that area for, as you may have guessed, demonstration purposes. The interface we use for this purpose is an HTML web page that makes various AJAX calls depending on the button you press. The screens were of a very simple design but for some reason this iPad just didn’t seem to be working right. The registering of the button press was hit and miss. This was our demonstration area and this thing needed to be rock solid so I had to dive into it and figure out what was going wrong.
The first thing I checked was the code. It’s simple HTML using anchor tags styled to look like iOS buttons. We used anchor tags because they could be styled the way we wanted them to be. The web page is built as an iOS home screen web app and so uses JavaScript to call the web resources for each button. We chose the “click” event of the anchor tag to fire the URL calls. This is pretty standard for web applications. The code seemed to be written right and we confirmed there were no HTML validation errors or JavaScript errors.
One thing that added to the confusion was we had CSS changing the style of the button when the link became active to indicate to the user that they were pressing the button. This CSS was obviously working because the button was changing colors. The confusing part is then that it was registering that the link was becoming active, just not firing the click event.
Next, I had our IT department swap out the iPad with a 2nd generation iPad which had all the iOS updates thinking perhaps it was a Safari or hardware issue. This turned out to not be the case.
So the next thing I did was to swap out the click event for the mousedown event, thinking that since the CSS was firing, then the mousedown event would fire. I was wrong. It still didn’t work properly. I did some digging into Apple’s documentation to find out that the mouseover, mousemove, mousedown, mouseup and click events all happen after the user lifts their finger from the screen (source). Turns out that they provide you with a few new events to work with user interaction on the screen in the touch environment: touchstart, touchend, touchmove and touchcancel (as well as a few others).
After discovering that, I switched the code to fire on the touchstart event and the screen worked perfect! Well… almost. The way we have the screen laid out, there are several sets of buttons arranged in a horizontal row. And if I were to press and hold one of these buttons, the button would fire as expected, but a few seconds after that, the other buttons would fire in succession and then loop back around firing all the buttons again. Now I was thoroughly confused.
To add to the confusion, there was only one single iPad displaying this behavior: the one installed in the demo area. I took my development iPad down to the demonstration area and attempted to reproduce the behavior in the environment with my iPad but couldn’t. Finally I decided to unplug and remove the installed (trouble) iPad and try with mine in the mount. I unplugged the installed iPad and decided for the sake of troubleshooting to try it once more while unplugged. Guess what. It worked perfect and displayed no weird behavior. Plugged it back in and sure enough it started flaking out again. Removed it from the mount while still plugged in and it worked fine again. Turns out a combination of being plugged in and in the mount was the ingredients for the perfect storm.
After consulting with a coworker to ensure I wasn’t insane (in hindsight it all makes sense, but while I was troubleshooting, it did not). Turns out it’s a grounding issue. I’m no expert in capacitive screens, but from what I gather, the simple of it is that the iPad was built to be held. So when you run it in a mount that is not grounded and have it running plugged in, because it doesn’t have a grounding reference, the capacitive screen could register ‘extra interaction’ with the screen.
As simple check I put it back in the mount plugged in and executed the test again, but this time, I touched the back of the iPad at the same time and it worked perfect. No extra interaction registered. Now, the next step is to attach some sort of grounding wire to the iPad and see if we can keep it working reliably without having to touch the back of it.
Again, the take-away of this post is that if you’re using an iPad as a touchscreen in some sort of display (not meant to be held), you may need to consider grounding the iPad to ensure it stays working correctly.
If you’re a developer, you undoubtedly know what the CRUD operations are: Create, Read, Update and Delete. These are the basic operations of persistent storage. They are also the basic operations you should adhere to when developing an MVC web application or web site. It will help you keep your MVC structure simple and clean. Developing with ASP.NET MVC3, Visual Studio has built in templates that stub in the CRUD operations for you.
However, these operations don’t always meet the need for the controller action. Sometimes you need to actually execute a command. Perhaps you’ve built an web frontend to a server and you’re providing the user with a way to shutdown or restart the server through said frontend. Or maybe you need to transmit a message over a communication network. In other words, perform an operation that doesn’t really interact with persistent storage or is a complex series of steps to complete that operation.
I was surprised when I did a Google search for “create read update delete execute”, the only results I found about it on the first page were definitions for the CRUDE acronym. The rest were about CRUD. I understand that these operations are typically referencing persistent storage, but with the popularity of MVC over the past few years, I’m surprised we haven’t seen more people extending these for operations to include Execute.
The take away is, when you’re building your MVC controller, try to stick to the CRUD operations, and when you have to move beyond them, ask yourself if you’re organizing your controllers and actions incorrectly and then ask yourself if the operation actually falls under the “execute” umbrella. It may help you structure your controller actions better.
If there is a way to set the open, send, receive, etc, timeouts on a web service call in MonoTouch, I haven’t found it yet. Been scouring Google to try to find it. In regular .NET, you modify the bindings in the application configuration file. I haven’t found the equivalent in MonoTouch yet. Though I’m not using the exact implementation, I’m using a similar implementation inspired by this blog post to enforce a timeout. My original problem was that the connection was timing out after about 2.5 minutes. I don’t want to wait that long to realize that the server is not there. This provides me with the functionality even if it is a bit of a brute force attack on the connection.
I recently ordered an item through Target.com. Today I tracked the package. This is my story.
Success!
One of the major gripes people have about e-commerce sites is that you have to create an account with the site in order to place an order. An old coworker of mine is a full-time SEO expert and had explained to me that you hurt your conversion rate when you require users to sign up for an account. I forget by how much you end up hurting your conversion rate, but it was substantial. A large enough number that you’d be a fool to not even consider the impact on your sales when making the decision to force users to register. So the alternative is to give them the option. Either they register and get all the benefits of order history, etc. or they just give you the minimum information: CC, shipping and billing address and an email address to send notifications about their order.
This is exactly how Target has their site designed. I loved it. One less account to keep track of. One less password to create and keep in my password manager.
So Target deserves a pat on the back for this.
Fail!
However, there’s another aspect of this whole experience that I was less thrilled about. That would be the shipment notification/tracking aspect. Let me outline the process as compared to other shipment notifications that I have received in the past and see if you can spot the difference.
Target
Other Site
Now, I understand the need for the secure link, etc for getting into my order details. I didn’t register for an account, so they need to make sure that they are securing the details of my order which includes snippets of my billing information. All of which, again, they did an excellent job on. However, for simply wanting to track my package and view nothing else about my order, that’s a LOT of steps. I also understand that tracking details might not have been received yet by the time the shipment notice email arrives to me (it said so right in the shipment notice email under the “Track this package” link). However, I’d appreciate a second email then with the actual shipping number.
Again, kudos Target on your design decisions around having guest orders and securing those orders. However, you may want to rethink how a user goes about getting shipment tracking details on a guest order and try to improve that experience.
BuckyBall Mushroom House
This is the photo that lead to the conversation that I should switch off of Blogger and onto Tumblr and start blogging again; so it seems fitting that it would be the first post on my new tumblelog.