Spinning out of control!
What's going on?
Well...I was wondering what control to explore this week. Currently I have my Sherlock hat on and trying to filter down the list of necessary controls using the Silverlight framework to meet the most common Rich Internet Application requirements. We have not received too many requests for Spinner/NumericUpDown but I thought I would try out how hard it is to come up with something using existing functionality in Silverlight. So here are some observations/findings.
A spinner or a numeric up/down control allows the user to choose values (from a collection that are in a predetermined order) by hitting two buttons that enumerate over the collection in either directions. The values can be dynamically generated (just plain integers, items pulled using a web service etc.) or from a static list (days of the week, months in a year etc.).
So where could a spinner be used?
These are some easy examples that come to my mind. I am sure a Spinner control could be re-purposed to do a lot more hence this attempt to find common ground.
Shopping carts: You can use a Spinner control to specify the quantity for an item being purchased. A user needs to hit up/down to increase or decrease the value or can also type in the exact value desired.
Paging controls: A lot of websites use paging controls when users need to sift through data. The user can specify the page number or hit next/previous to navigate through.
Picture SlideShow: Navigate through pictures using previous/next buttons.
Do other frameworks have a Spinner?
Here are some existing implementations that support
Windows Forms: This one provides purely numeric functionality i.e. the content that can be spun can only be numbers. It does allow some interesting formatting options.
WPF NumericUpDown: Simple numeric up/down functionality. Not part of the official offering (in the SDK).
AJAX Control Toolkit: Allows for non-numeric as well as numeric data. Data can be pulled from a web-service or can be statically bound as well.
My attempts at Spinning...
Big Disclaimer: Do not expect anything pretty :(.Excuse my poor designer skills. I did create better-looking arrows using Expression design but was limited by time constraints and the inability to resize the paths in my designs because of the lack of ViewBox in Silverlight. Note to self: need to have ViewBox.
All of these trials use two RepeatButtons but you could choose to use a regular Button as well if you do not want to RepeatButton style clicking. None of these are controls or user controls, just my attempts to see how I can get spinning functionality in place. I will write another blog post that talks about a packaged Spinner control that can be configured to have this functionality.
With a TextBox
I started with the idea that I should be able to simply update the number in a TextBox by parsing the existing contents.
- This one was pretty straightforward just snap in a TextBox and two RepeatButtons.
- Having a RepeatButton instead of a regular Button allows me to quickly increment/decrement without having to mouse down and up multiple times. Although, just swapping in a Button instead will still just work.
- I placed the RepeatButtons on either side of the TextBox to demonstrate that you could have a simple paging control with little effort. I update the number in the click handlers of the two buttons.
- You are pretty much tied to numeric values and cannot exploit other data-types.
- I do not perform any formatting/masking on the numbers.
With a ListBox
My main motivation here was to bind to a set of values and navigate through them showing only one of them at a time. My team mate, David, does a SlideShow using the same principle and I used that as an inspiration. I hide the scroll bars and configure it such that only one item can be seen at a time.
- Databinding is taken care of and works easily for both static and dynamic data.
- Buttons can be disabled/enabled based on items left to spin to in either direction.
- ListBox introduces too much size and functionality overhead in terms of its template and scrolling. The latter is disabled in this case.
- Need a little bit of manual tweaking to get just one item to display. It is too hard-coded to the item size and may not be very flexible if the data-types change.
With a ContentControl
The idea here was to navigate across and choose any kind of content. In the picture below I use a TextBox in the DataTemplate whose Text property is bound to the Content property of the ContentControl.
Usage scenarios that come to my mind are slide shows, menus, just plain numeric up/down, combo-box style TextBoxes etc. all that will light up with data templating.
I had to manage the data binding tasks manually since I did not have the built-in support of an ItemsControl but it could still be managed. I will give it a shot in my next blog post.
To wrap up...
I have attached the solution based on the Silverlight 2 Beta 1 bits that includes the source code for all the three samples. Again, it is not in a super-reusable form and purely includes some simple event handling behind the scenes to achieve this scenario with existing Silverlight components. I will attempt to release a more reusable version very soon.
Let me know what are your most important requirements from a Spinner. Those should help me a great deal!