How to achieve this advanced interface with jQuery?
<p>I'm currently fighting a fierce battle with an interface I'm trying to put together. I'm pretty decent at CSS &amp; XHTML, but my jQuery/JavaScript skills are not too impressive. What I'm looking for is not so much a strict answer, but some hints on how to go about these kinds of tasks. </p>

<p>What I am trying to achieve is a layout with some boxes in the main-content area that can be expanded and collapsed when the user press either a link in the sidebar or on a header on the box itself. </p>

<p><img src="http://www.timkjaerlange.com/foobar/example-dashboard-v01.gif" alt="dashboard"></p>

<p>Furthermore I want the browser to remember what box was expanded last by setting a cookie. If that wasn't enough I also want to be able to add a "limited"-class to each box and thereby disabling it, and it's corresponding sidebar-list-item.</p>

<p>Also I want the box to have a class based on it's state (expanded, collapsed, limited).</p>

<p>This is my markup:</p>

<pre><code>&lt;!-- S I D E B A R - L E F T --&gt;    

&lt;div id="sidebar-left"&gt;
    &lt;ul class="sidebar-menu-1"&gt;
     &lt;li&gt;&lt;strong&gt;List headline&lt;/strong&gt;
     &lt;/li&gt;
     &lt;li&gt;&lt;a href="#"&gt;Open module 1&lt;/a&gt;
     &lt;/li&gt;
     &lt;li&gt;&lt;a href="#"&gt;Open module 2&lt;/a&gt;
     &lt;/li&gt;
     &lt;li&gt;&lt;a href="#"&gt;Open module 3&lt;/a&gt;
     &lt;/li&gt;
    &lt;/ul&gt;

&lt;/div&gt;&lt;!--/sidebar-left--&gt;


&lt;!-- M A I N - C O N T E N T --&gt;    

&lt;div id="main-content"&gt;

    &lt;!-- dashboard-module --&gt;
    &lt;div class="dashboard-module"&gt;
    &lt;div class="dashboard-module-content limited"&gt;
     &lt;h2&gt;Headline 1&lt;/h2&gt;
     &lt;p class="teaser"&gt;Teaser-text 1&lt;/p&gt;
     &lt;div class="expand-collapse"&gt;
      [some content]
    ´ &lt;/div&gt;
    &lt;/div&gt;
    &lt;/div&gt;&lt;!--/dashboard-module--&gt;


    &lt;!-- dashboard-module --&gt;
    &lt;div class="dashboard-module"&gt;
    &lt;div class="dashboard-module-content limited"&gt;
     &lt;h2&gt;Headline 2&lt;/h2&gt;
     &lt;p class="teaser"&gt;Teaser-text 2&lt;/p&gt;
     &lt;div class="expand-collapse"&gt;
      [some content]
    ´ &lt;/div&gt;
    &lt;/div&gt;
    &lt;/div&gt;&lt;!--/dashboard-module--&gt;


    &lt;!-- dashboard-module --&gt;
    &lt;div class="dashboard-module"&gt;
    &lt;div class="dashboard-module-content limited"&gt;
     &lt;h2&gt;Headline 3&lt;/h2&gt;
     &lt;p class="teaser"&gt;Teaser-text 3&lt;/p&gt;
     &lt;div class="expand-collapse"&gt;
      [some content]
    ´ &lt;/div&gt;
    &lt;/div&gt;
    &lt;/div&gt;&lt;!--/dashboard-module--&gt;


&lt;/div&gt;&lt;!--/main-content--&gt;
</code></pre>

<p>And this is my jQuery: </p>

<pre><code>// If the dashboard-module is "limited" do this:

$('div[class*=limited]').each( function(index) {
    var countFix = $('div.dashboard-module-content').index(this);
    var countFixPlusTwo = countFix + 2;
    $( 'ul.sidebar-menu-1 li:nth-child(' + countFixPlusTwo + ')' ).unbind('click').removeClass('selected').addClass('sidebar-menu-locked');
    $(this).parent('.dashboard-module').find('h2').unbind('click');
    $(this).find('.expand-collapse').remove();
    $(this).find('.dashboard-module p:hidden').show();
    $(this).addClass('limited-btn');
});

// Check for cookies and do stuff accordingly:

var cookieTest = $.cookie("cookie");

if(cookieTest == null){
    $('.js-hidden').hide();
    $('ul.sidebar-menu-1 li:not(.sidebar-menu-locked):eq(1)').addClass('selected');
    $('.dashboard-module-content:not(.limited):eq(0)' ).toggleClass('hide-btn'); 
    $('.dashboard-module-content:not(.limited):not(:eq(0))' ).removeClass('hide-btn');
    $('.expand-collapse:eq(0)' ).show();
    };

if(cookieTest != null){
    var cookieTestPlusTwo = parseInt(cookieTest, 10) + 2;
    $('.dashboard-module-content:eq(' + cookieTest + ')' ).toggleClass('hide-btn'); 
    $('.dashboard-module-content:not(:eq(' + cookieTest + '))' ).removeClass('hide-btn'); 
    $('ul.sidebar-menu-1 li:nth-child(' + cookieTestPlusTwo + '):not(.sidebar-menu-locked)').addClass('selected');
    $('ul.sidebar-menu-1 li:not(:nth-child(' + cookieTestPlusTwo + '))').removeClass('selected');
    $('.expand-collapse:eq(' + cookieTest +  ')' ).show();
    $('.expand-collapse:not(:eq(' + cookieTest +  '))').hide();
    };

// When clicking dashboard-module headers do stuff:

$('.dashboard-module h2:not(.limited h2):not(.tooltip h2)').click(function(index) {

    var indexFoo = $('.dashboard-module h2:not(.tooltip h2)').index(this);
    var indexPlusTwo = indexFoo + 2;
    var indexCookie = indexFoo;

    $.cookie("cookie", indexCookie, { expires: 7 });

    $('.dashboard-module-content:eq(' + indexFoo + ')').toggleClass('hide-btn'); 
    $('.dashboard-module-content:not(:eq(' + indexFoo + '))' ).removeClass('hide-btn');

    $('ul.sidebar-menu-1 li:nth-child(' + indexPlusTwo + ')').addClass('selected');
    $('ul.sidebar-menu-1 li:not(:nth-child(' + indexPlusTwo + '))').removeClass('selected');

    $('.dashboard-module-content:eq(' + indexFoo + ') .expand-collapse').toggle('fast');
    $('.dashboard-module-content:not(:eq(' + indexFoo + ')) .expand-collapse').hide('fast');

    $('.dashboard-module-content:not(.limited)').each( function(){
     if($(this).parent('.dashboard-module').find('.hide-btn').length == 0){
      $(this).find('p.teaser').show();
     }
     else {
      $(this).find('p.teaser').hide();
     }
    });
});

// When clicking sidebar list-items do stuff:

$('.sidebar-menu-1 li:not(.sidebar-menu-locked)').click(function(index) {

    var indexFoo = ($('.sidebar-menu-1 li').index(this) - 1);
    var indexPlusTwo = indexFoo + 2;
    var indexCookie = indexFoo;

    $.cookie("cookie", indexCookie, { expires: 7 });

    $('.dashboard-module-content:eq(' + indexFoo + ')').toggleClass('hide-btn'); 
    $('.dashboard-module-content:not(:eq(' + indexFoo + '))' ).removeClass('hide-btn'); 

    $('ul.sidebar-menu-1 li:nth-child(' + indexPlusTwo + ')').addClass('selected');
    $('ul.sidebar-menu-1 li:not(:nth-child(' + indexPlusTwo + '))').removeClass('selected');

    $('.dashboard-module-content:eq(' + indexFoo + ') .expand-collapse').toggle('fast');
    $('.dashboard-module-content:not(:eq(' + indexFoo + ')) .expand-collapse').hide('fast');

    $('.dashboard-module-content:not(.limited)').each( function(){
     if($(this).parent('.dashboard-module:not(.limited)').find('.hide-btn').length == 0){
      $(this).find('p.teaser').show();
     }
     else {
      $(this).find('p.teaser').hide();
     }
    });

});
</code></pre>

<p>As for now it all works in FF, but in IE7+8 it doesn't. But my question is not so much about how to make it work in IE, but more on how you would go about this kind of task? I suspect that my jQuery is not exactly DRY, but how do I condense it?</p>

<p>How would you write and organize your code? Sorry if this is a too broad and long-winded question, but I'm really interested in how experienced jQuery designers go about challenges like this one.</p>

<p><strong>Update:</strong> Thanks to Tatu Ulmanen's help I've managed to put together this: <a href="http://timkjaerlange.com/foobar/jquery-test/index.html" rel="nofollow">http://timkjaerlange.com/foobar/jquery-test/index.html</a></p>
