views:

103

answers:

4

I'm creating a live mockup for a client website, and I'm having some problems getting the design to work.

The site master has a menu that has multiple categories, but they all contain similar content. I need the menu to remember which one was selected. So I tried setting a cookie that would remember which category was last accessed, and leave that highlighted for the user. (I know this probably isn't the proper way to do it, but it's a mockup and I just want to get it done. Brute force is acceptable).

Here is my embarassingly bad code, inlined on the master page:

protected override void OnInit(EventArgs e)
  {
      base.OnInit(e);

      switch (Path.GetFileNameWithoutExtension(HttpContext.Current.Request.Url.AbsolutePath).ToLower())
      {
          case "category1":
              HttpContext.Current.Response.Cookies.Add(new HttpCookie("selectedCategory", "category1"));
              break;
          case "category2":
              HttpContext.Current.Response.Cookies.Add(new HttpCookie("selectedCategory", "category2"));
              break;
          ...
          case "default":
              HttpContext.Current.Response.Cookies.Add(new HttpCookie("selectedCategory", "category1"));
              break;
      }
  }

// filePath will be "category1", "category2", etc.
public string IsSelected(string filePath) 
{
    return String.Compare(HttpContext.Current.Request.Cookies["selectedCategory"].Value, filePath, true) == 0
               ? " selected" // The class name to add to the CSS
               : String.Empty;
}

And the links just call IsSelected with the name "category1", "category2" etc.

<li class="menu<%=IsSelected("category1") %>"><a href="/Category1.aspx">

My problem is that the cookie is always a page behind. If I go from category1 to category2, category1 stays highlighted. If I continue to category3, now category2 is highlighted.

What I don't understand is that when I set breakpoints, the cookies value is being set to the proper page, but it's being read out wrong. Can I not do this at all?

Can anyone tell me what is wrong or a way to fix this?

+1  A: 

One way - maybe not the best way - to share some data on the current request is to use the httpRequest.Context.Current.Items container. Then you can pluck out your values youwant to en-cookie-ize somewhere at the end of your request processing (PostRender maybe? Is that even an event?)

No Refunds No Returns
+1, thanks for the suggestion.
Brandon
+2  A: 

All cookies you add/delete will be available/deleted only on next request. This is because cookies belongs to a client browser and HttpContext.Current.Response.Cookies returns cookies that come with current request.
Consider using Session or HttpContext.Current.Items for this task.

zihotki
+1, I never really used cookies for something like this. Didn't consider that it wouldn't yet be in the current request. I switched to using session. Thanks for the suggestion.
Brandon
+1  A: 

You are (properly) adding cookies to the Response.Cookies collection during OnInit, but your IsSelected property checks the Request.Cookies. Adding a cookie to the response does not automatically add it to the current request as well (as far as I know).

Have you tried looking for the selectedCategory cookie in both Request.Cookies and Response.Cookies, to handle the special case when the cookie is set in the current request? I'm actually not sure this would work, but maybe worth a try?

Anders Fjeldstad
+1, it didn't work for what I needed to do, but thanks for the suggestion.
Brandon
+1  A: 

Cookie handling hasn't changed as much as I have in the 7 years since I wrote this:

http://www.codeproject.com/KB/aspnet/aspnetcookies.aspx?df=100&amp;forumid=13312&amp;exp=0&amp;fr=26

pdr