MediaWiki:Common.js: Difference between revisions

From SZ
Jump to navigation Jump to search
No edit summary
No edit summary
Line 34: Line 34:
     //var $panels = $('#mw-panel .vector-menu-portal, .vector-menu-portal', $root);
     //var $panels = $('#mw-panel .vector-menu-portal, .vector-menu-portal', $root);
var $panels = $('#mw-panel .vector-menu-portal, #mw-panel .vector-menu.mw-portlet', $root);
var $panels = $('#mw-panel .vector-menu-portal, #mw-panel .vector-menu.mw-portlet', $root);


     if (!$panels.length) {
     if (!$panels.length) {

Revision as of 20:43, 25 August 2025

/**
 * Collapsible Sidebar (Debug Build) for MW 1.44 (Vector + Vector 2022)
 * - Writes verbose logs to the console
 * - Inserts a real <span> arrow (▶), so you see it even if :before fails
 * - No jquery.cookie, no extra modules
 *
 * Toggle logging at runtime with: window.MWSidebarDebug = true/false
 */
(function () {
  // Turn on debug by default; you can turn off in the console if too chatty.
  window.MWSidebarDebug = true;

  function log() {
    if (window.MWSidebarDebug && typeof console !== 'undefined') {
      console.log.apply(console, ['[SidebarCollapsible]'].concat([].slice.call(arguments)));
    }
  }
  function warn() {
    if (typeof console !== 'undefined') {
      console.warn.apply(console, ['[SidebarCollapsible]'].concat([].slice.call(arguments)));
    }
  }

  var skin = mw.config.get('skin');
  log('Init start. Detected skin =', skin);

  function findTopList($panel) {
    // Works for Vector/Vector-2022 portlets and (fallback) legacy .portal markup
    return $panel.find('> .vector-menu-content > .vector-menu-content-list, > .body > ul').first();
  }

  function initOnce($root) {
    // Find all sidebar portlets that look like menus
    //var $panels = $('#mw-panel .vector-menu-portal, .vector-menu-portal', $root);
var $panels = $('#mw-panel .vector-menu-portal, #mw-panel .vector-menu.mw-portlet', $root);


    if (!$panels.length) {
      warn('No .vector-menu-portal found. Are you using Vector/Vector-2022?');
    } else {
      log('Found', $panels.length, 'portal(s).');
    }

    $panels.each(function (idx, el) {
      var $panel = $(el);
      var id = $panel.attr('id') || ('panel#' + idx);
      var $list = findTopList($panel);

      if (!$list.length) {
        warn('Panel has no UL list:', id, $panel.get(0));
        return;
      }

      var $items = $list.children('li');
      log('Panel', id, ':', $items.length, 'top-level <li> item(s).');

      $items.each(function (i, li) {
        var $li = $(li);
        var $sub = $li.children('ul');

        if (!$sub.length) {
          // Not a collapsible candidate
          return;
        }

        // Mark as collapsible and hide sub-list (if not already)
        $li.addClass('collapsible-header');
        if (!$li.children('.mw-collapsible-arrow').length) {
          // Insert a real arrow character so it’s guaranteed visible
          $li.prepend($('<span class="mw-collapsible-arrow" aria-hidden="true">▶</span>'));
        }
        $sub.hide();

        // Log header text for reference
        var headerText = ($li.find('> a').first().text() || $li.clone().children().remove().end().text() || '')
          .trim()
          .replace(/\s+/g, ' ');
        log('Registered collapsible item', i, 'in', id, 'header=', headerText);

        // Click to toggle (but let actual links work)
        $li.off('.mwCollapsibleSidebar')  // avoid duplicate binding
          .on('click.mwCollapsibleSidebar', function (e) {
            if ($(e.target).closest('a').length) {
              // Click on a link inside; do not toggle
              log('Link click passthrough for header:', headerText);
              return;
            }
            e.preventDefault();
            var willOpen = !$li.hasClass('open');
            $li.toggleClass('open');
            $sub.stop(true, true).slideToggle(200);
            log('Toggled', (willOpen ? 'open' : 'closed') + ':', headerText);
          });
      });
    });
  }

  // Run on DOM ready and on content re-renders
  mw.loader.using('mediawiki.util').then(function () {
    $(function () {
      console.group && console.group('[SidebarCollapsible] bootstrap');
      initOnce($(document));
      console.groupEnd && console.groupEnd();
    });
    mw.hook('wikipage.content').add(function ($c) {
      log('wikipage.content hook fired (re-init on dynamic content).');
      initOnce($c);
    });
  });
})();