Let’s say I want the user to select their favorite theme for my application. I can make a list of available themes in a DropDownList control.
I know I must set the Theme property before or during the page’s PreInit event.
What’s wrong with the following code?
The above code throws a null reference exception. PreInit fires before the page instantiates its controls, so _themeList is null (Nothing). I can’t use the _themeList control, but I can go directly to the Request.Form collection. The DropDownList (an HTML select) will post its new value into the form collection.
What could go wrong with this code?
Hint: this code will work for many webforms, but not if you are using a master page.
The problem with asking for “_themeList” is that “_themeList” is a server side ID. The browser will submit the form with a unique client side ID. If the DropDownList ends up inside an INamingContainer, the UniqueID property is not the same as the ID property (see my FindControl article for more on INamingContainer). If the DropDownList is on a master page, the UniqueID might look like “ctl00$_themeList”. If the DropDownList is inside a ContentPlaceHolder control, the UniqueID might look like "ctl00$ContentPlaceHolder1$_themeList" .
There are many ways to solve the problem. One solution might be a brute force search of the form collection for a key ending with “_themeList”. Another approach is to stash the list's UniqueID into a hidden form field.
I’m sure you can think of some other elegant ways to solve the problem. The trick, as always, is finding out what the problem really is.
Comments
That one's bitten me more than a few times as well and the first couple of times (I can be a slow learner) it took me a while to figure out that the MasterPage was changing the containership :-}...
The problem in PreInit is that the the list isn't set yet and SelectedValue won't have its value set so it'll certainly be null.
Jimh
Great article. One thing I cannot find and don't think is possible is that everything points to the fact that you can only change a PAGE'S theme, but it is NOT possible to change the APPLICATION'S theme programmatically via a user's input. So, in your example, you cannot have a user select from the dropdownlist a theme that will carry over to all the pages in the application. I realize that you can change the application's theme by hard-coding in the web.config. Is this a limitation with using themes in ASP.NET 2.0?
Thanks in advance,
Harry
Access using MAsterpages needs to be rethought by MS.
Article helped me alot....thanks...
Cheerio...
Here is my solution for applying theme programatically to the whole website: www.4invent.com. Actually the method is used in the blog where the post is published, every user will have the ability to have it's own template selected from a list or to build a css file by itself. Let me know if you need assistance.
Claudiu
String eventTarget = Request.Form["__EVENTTARGET"];
if (eventTarget == "Radio_Soy")
{
Theme = "Soy";
}
else if (eventTarget == "Radio_Mocha")
{Theme = "Mocha";
}
Request.Form["ctl00$PlaceHolderMain$DropDLLanguage"]
really helpful.