XF 2.2 Collapsing/expanding sidebar widgets

valdet

Active member
I didn't post this in Suggestions forum, because as it is a common (obvious) feature in websites, it may have been suggested before, but this is a fairly simple suggestion for which I think it would help with forums that could have too many sidebar widgets.

It would be really helpful to be able to have the widgets collapse (or expand), similar to how categories work.

1709904382827.webp

A quick sample which also saves the state of the widget between session/pageviews, whether it is collapsed or not

HTML:

HTML:
<div class="widget">
  <p align="right" class="expand"><a href="#">🔽</a></p>
  <p class="content">This is the Xenforo widget content</p>
</div>

Javascript:
Code:
// Check if there's a saved state in localStorage and apply it
$(document).ready(function() {
  $('.content').each(function() {
    var $this = $(this);
    var isOpen = localStorage.getItem('content_' + $this.index());
    if (isOpen === 'true') {
      $this.show();
      $this.closest('.widget').find('.expand a').text('🔼');
      $this.closest('.widget').find('.expand img').hide();
    } else {
      $this.hide();
    }
  });
});

$('.expand').click(function() {
  var $expandButton = $(this).find('a'); // Select the anchor tag inside .expand-one
  var $content = $(this).closest('.widget').find('.content');
  $content.slideToggle('slow', function() {
    var $this = $(this);
    if ($this.is(':visible')) {
      $expandButton.text('🔼');
      $expandButton.find('img').hide();
      localStorage.setItem('content_' + $this.index(), true);
    } else {
      $expandButton.text('🔽');
      $expandButton.find('img').show();
      localStorage.setItem('content_' + $this.index(), false);
    }
  });
});

Preview:

It is fairly straightforward in HTML, but the question is how to do this in Xenforo?
I couldn't find the default widget wrapper, where I would "hack" this code into, so I hope there's a quick way to do this.

Thanks.
 
Last edited:
I just replaced this in node_list_category template and works fine for me. it is right in the begining of the template.

HTML:
<xf:macro name="depth1" arg-node="!" arg-extras="!" arg-children="!" arg-childExtras="!" arg-depth="1">
    <div class="block block--category block--category{$node.node_id}">
        <span class="u-anchorTarget" id="{$node.Data.getCategoryAnchor()}"></span>
        <div class="block-container">
            <h2 class="block-header">
                <div class="bh--left">
                    <a href="{{ link('categories', $node) }}">{$node.title}</a>
                    <xf:if is="{$node.description}"><span class="block-desc">{$node.description|raw}</span></xf:if>
                </div>
                <div class="bh--right">
                    <span id="collapse-{$node.node_id}" class="collapseTrigger collapseTrigger--block {{ !is_toggled('_node-' . $node.node_id) ? ' is-active' : '' }}" data-xf-click="toggle" data-xf-init="toggle-storage" data-storage-type="cookie" data-target=".block--category{$node.node_id} .block-body" data-storage-key="_node-{$node.node_id}"></span>
                </div>
            </h2>
            <div class="block-body block-body--collapsible {{ !is_toggled('_node-' . $node.node_id) ? ' is-active' : '' }} flexer">
                <xf:macro template="forum_list" name="node_list"
                    arg-children="{$children}"
                    arg-extras="{$childExtras}"
                    arg-depth="{{ $depth + 1 }}" />
            </div>
        </div>
    </div>
</xf:macro>
 
Back
Top Bottom