Massive sidebar cleanup.
authorMichael M Slusarz <slusarz@curecanti.org>
Thu, 15 Jul 2010 19:07:44 +0000 (13:07 -0600)
committerMichael M Slusarz <slusarz@curecanti.org>
Thu, 15 Jul 2010 19:10:27 +0000 (13:10 -0600)
Move ajax request (i.e. 'httpclient') to the Horde Ajax framework.
Fix broken javascript - it was still referring to frames and
wasn't properly resizing body on sidebar toggle.

framework/Core/lib/Horde/Core/Tree/Javascript.php
horde/js/hordetree.js
horde/js/sidebar.js
horde/lib/Ajax/Application.php [new file with mode: 0644]
horde/lib/Ui/Sidebar.php [new file with mode: 0644]
horde/services/portal/sidebar.php
horde/templates/portal/sidebar.inc

index 0407e04..e022ed4 100644 (file)
@@ -92,12 +92,13 @@ class Horde_Core_Tree_Javascript extends Horde_Core_Tree_Html
             'imgNullOnly' => $this->_images['null_only'],
             'imgLeaf' => $this->_images['leaf'],
 
-            'floatDir' => (empty($GLOBALS['registry']->nlsconfig['rtl'][$GLOBALS['language']]) ? 'float:left;' : 'float:right')
+            'floatDir' => (empty($GLOBALS['registry']->nlsconfig['rtl'][$GLOBALS['language']]) ? 'float:left;' : 'float:right'),
+
+            'initTree' => $this->renderNodeDefinitions()
         );
 
         Horde::addInlineScript(array(
-            'window.' . $this->_instance . ' = new Horde_Tree(' . Horde_Serialize::serialize($opts, Horde_Serialize::JSON, $GLOBALS['registry']->getCharset()) . ')',
-            $this->renderNodeDefinitions()
+            'window.' . $this->_instance . ' = new Horde_Tree(' . Horde_Serialize::serialize($opts, Horde_Serialize::JSON, $GLOBALS['registry']->getCharset()) . ')'
         ), 'dom');
 
         return '<div id="' . $this->_instance . '"></div>';
@@ -117,13 +118,17 @@ class Horde_Core_Tree_Javascript extends Horde_Core_Tree_Html
     /**
      * Returns just the JS node definitions as a string.
      *
-     * @return string  The Javascript node array definitions.
+     * @return array  The following keys: 'is_static', 'nodes', 'root_nodes'.
      */
     public function renderNodeDefinitions()
     {
         $this->_buildIndents($this->_root_nodes);
 
-        return 'window.' . $this->_instance . '.renderTree(' . Horde_Serialize::serialize($this->_nodes, Horde_Serialize::JSON, $GLOBALS['registry']->getCharset()) . ',' . Horde_Serialize::serialize($this->_root_nodes, Horde_Serialize::JSON, $GLOBALS['registry']->getCharset()) . ',' . ($this->_static ? 'true' : 'false') . ');';
+        return array(
+            'is_static' => intval($this->_static),
+            'nodes' => $this->_nodes,
+            'root_nodes' => $this->_root_nodes
+        );
     }
 
 }
index 984b047..d665aae 100644 (file)
@@ -7,7 +7,7 @@
  * did not receive this file, see http://www.fsf.org/copyleft/gpl.html.
  *
  * @author   Marko Djukic <marko@oblo.com>
- * @author   Michael Slusarz <slusarz@curecanti.org>
+ * @author   Michael Slusarz <slusarz@horde.org>
  * @category Horde
  */
 
@@ -16,6 +16,11 @@ var Horde_Tree = Class.create({
     initialize: function(opts)
     {
         this.opts = opts;
+
+        if (this.opts.initTree) {
+            this.renderTree(this.opts.initTree.nodes, this.opts.initTree.root_nodes, this.opts.initTree.is_static);
+            this.opts.initTree = null;
+        }
     },
 
     renderTree: function(nodes, rootNodes, renderStatic)
index ea501c2..0cfa7c5 100644 (file)
@@ -6,6 +6,8 @@
  */
 
 var HordeSidebar = {
+    // Variables set in services/portal/sidebar.php:
+    // domain, path, refresh, rtl, tree, url, width
 
     getCookie: function(name, deflt)
     {
@@ -15,51 +17,52 @@ var HordeSidebar = {
             : deflt;
     },
 
-    toggleMenuFrame: function()
+    toggleSidebar: function()
     {
-        if (!parent || !parent.document.getElementById('hf')) {
-            return;
-        }
-
-        var cols,
+        var expanded = $('expandedSidebar').visible(),
             expires = new Date(),
-            rtl = horde_sidebar_rtl;
-        if ($('expandedSidebar').visible()) {
-            cols = rtl ? '*,20' : '20,*';
-        } else {
-            cols = (rtl ? '*,' : '') + horde_sidebar_cols + (rtl ? '' : ',*');
-        }
-        parent.document.getElementById('hf').setAttribute('cols', cols);
+            margin;
+
         $('expandedSidebar', 'hiddenSidebar').invoke('toggle');
         if ($('themelogo')) {
             $('themelogo').toggle();
         }
 
+        margin = expanded
+            ? $('hiddenSidebar').down().getWidth()
+            : this.width;
+        if (this.rtl) {
+            $('horde_body').setStyle({ marginRight: margin + 'px' });
+        } else {
+            $('horde_body').setStyle({ marginLeft: margin + 'px' });
+        }
+
         // Expire in one year.
         expires.setTime(expires.getTime() + 31536000000);
-        document.cookie = 'horde_sidebar_expanded=' + $('expandedSidebar').visible() + ';DOMAIN=' + horde_sidebar_domain + ';PATH=' + horde_sidebar_path + ';expires=' + expires.toGMTString();
+        document.cookie = 'horde_sidebar_expanded=' + !expanded + ';DOMAIN=' + this.domain + ';PATH=' + this.path + ';expires=' + expires.toGMTString();
     },
 
     updateSidebar: function()
     {
-        new Ajax.PeriodicalUpdater(
-            'horde_menu',
-            horde_sidebar_url,
-            {
-                parameters: { httpclient: 1 },
-                method: 'get',
-                evalScripts: true,
-                frequency: horde_sidebar_refresh,
-                onSuccess: function ()
-                {
-                    var layout = $('horde_menu').getLayout();
-                    $('horde_menu').setStyle({
-                        width: layout.get('width') + 'px',
-                        height: layout.get('height') + 'px'
-                    });
-                }
-            }
-        );
+        new PeriodicalExecuter(function() {
+            new Ajax.Request(this.url, {
+                onComplete: this.onUpdateSidebar.bind(this)
+            });
+        }.bind(this), this.refresh);
+    },
+
+    onUpdateSidebar: function(response)
+    {
+        var layout, r;
+
+        if (request.responseJSON) {
+            $('HordeSidebar.tree').update();
+
+            r = request.responseJSON;
+            this.tree.renderTree(r.nodes, r.root_nodes, r.is_static);
+
+            this.resizeSidebar();
+        }
     }
 
 };
@@ -67,9 +70,11 @@ var HordeSidebar = {
 document.observe('dom:loaded', function() {
     $('hiddenSidebar').hide();
     if (HordeSidebar.getCookie('horde_sidebar_expanded', true).toString() != $('expandedSidebar').visible().toString()) {
-        HordeSidebar.toggleMenuFrame();
+        HordeSidebar.toggleSidebar();
     }
-    if (horde_sidebar_refresh) {
-        HordeSidebar.updateSidebar.delay(horde_sidebar_refresh);
+    if (HordeSidebar.refresh) {
+        HordeSidebar.updateSidebar.bind(HordeSidebar).delay(HordeSidebar.refresh);
     }
+
+    $('expandButton', 'hiddenSidebar').invoke('observe', 'click', HordeSidebar.toggleSidebar.bind(HordeSidebar));
 });
diff --git a/horde/lib/Ajax/Application.php b/horde/lib/Ajax/Application.php
new file mode 100644 (file)
index 0000000..9974e68
--- /dev/null
@@ -0,0 +1,42 @@
+<?php
+/**
+ * Defines the AJAX interface for Horde.
+ *
+ * Copyright 2010 The Horde Project (http://www.horde.org/)
+ *
+ * See the enclosed file COPYING for license information (LGPL). If you
+ * did not receive this file, see http://www.fsf.org/copyleft/lgpl.html.
+ *
+ * @author   Michael Slusarz <slusarz@horde.org>
+ * @category Horde
+ * @license  http://www.fsf.org/copyleft/lgpl.html LGPL
+ * @package  Horde
+ */
+class Horde_Ajax_Application extends Horde_Ajax_Application_Base
+{
+    /**
+     * AJAX action: Update sidebar.
+     *
+     * @return stdClass  An object with the following entries:
+     * <pre>
+     * 'is_static'
+     * 'nodes'
+     * 'root_nodes'
+     * </pre>
+     */
+    public function sidebarUpdate()
+    {
+        $sidebar = new Horde_Ui_Sidebar();
+        $tree = $sidebar->getTree();
+
+        $defs = $tree->renderNodeDefinitions();
+
+        $result = new stdClass;
+        $result->is_static = $defs['is_static'];
+        $result->nodes = $defs['nodes'];
+        $result->root_nodes = $defs['root_nodes'];
+
+        return $result;
+    }
+
+}
diff --git a/horde/lib/Ui/Sidebar.php b/horde/lib/Ui/Sidebar.php
new file mode 100644 (file)
index 0000000..2600d33
--- /dev/null
@@ -0,0 +1,246 @@
+<?php
+/**
+ * The Horde_Ui_Sidebar:: class is designed to provide a place to store common
+ * code for sidebar generation.
+ *
+ * Copyright 2010 The Horde Project (http://www.horde.org/)
+ *
+ * See the enclosed file COPYING for license information (LGPL). If you
+ * did not receive this file, see http://www.fsf.org/copyleft/lgpl.html.
+ *
+ * @author   Michael Slusarz <slusarz@horde.org>
+ * @category Horde
+ * @license  http://www.fsf.org/copyleft/lgpl.html LGPL
+ * @package  Horde
+ */
+class Horde_Ui_Sidebar
+{
+    /**
+     * Generate the sidebar tree object.
+     *
+     * @return Horde_Tree  The sidebar tree object.
+     */
+    public function getTree()
+    {
+        global $conf, $injector, $prefs, $registry;
+
+        $apps = $cache = $children = $menu = array();
+
+        $isAdmin = $registry->isAdmin();
+        $user = $registry->getAuth();
+        foreach ($registry->applications as $app => $params) {
+            $curr_app = empty($params['app'])
+                ? $app
+                : $params['app'];
+
+            if (!isset($cache[$curr_app])) {
+                /* Check if the current user has permisson to see this
+                 * application, and if the application is active. Headings are
+                 * visible to everyone (but get filtered out later if they
+                 * have no children). Administrators always see all
+                 * applications except those marked 'inactive'. Anyone with
+                 * SHOW permissions can see an application, but READ is needed
+                 * to actually use the application. You can use this
+                 * distinction to show applications to guests that they need
+                 * to log in to use. If you don't want them to see apps they
+                 * can't use, then don't give guests SHOW permissions to
+                 * anything. */
+
+                /* Don't show applications that aren't installed, even if
+                 * they're configured.
+                 * -OR-
+                 * Don't show blocks of applications that aren't installed.
+                 * -OR-
+                 * Filter out entries that are disabled, hidden or shouldn't
+                 * show up in the menu. */
+                if ((isset($params['fileroot']) &&
+                     !is_dir($params['fileroot'])) ||
+                    (($params['status'] == 'block') &&
+                     !is_dir($registry->get('fileroot', $params['app']))) ||
+                    (in_array($params['status'], array('hidden', 'inactive', 'notoolbar')))) {
+                    $cache[$curr_app] = false;
+                } elseif (($params['status'] == 'heading') ||
+                          ($isAdmin ||
+                           ($registry->hasPermission($curr_app, Horde_Perms::SHOW) &&
+                            (($params['status'] == 'active') ||
+                             ($params['status'] == 'block'))))) {
+                    $cache[$curr_app] = true;
+
+                    // Note that the parent node, if any, has children.
+                    if (isset($params['menu_parent'])) {
+                        $children[$params['menu_parent']] = true;
+                    }
+                } else {
+                    // Catch anything that fell through, and don't show it.
+                    $cache[$curr_app] = false;
+                }
+            }
+
+            if ($cache[$curr_app]) {
+                $apps[$app] = $params;
+            }
+        }
+
+        foreach ($apps as $app => $params) {
+            // Filter out all headings without children.
+            if (($params['status'] != 'heading') || !empty($children[$app])) {
+                $menu[$app] = $params;
+            }
+        }
+
+        // Add the administration menu if the user is an admin.
+        if ($registry->isAdmin()) {
+            $menu['administration'] = array(
+                'name' => _("Administration"),
+                'icon' => strval(Horde_Themes::img('administration.png')),
+                'status' => 'heading'
+            );
+
+            try {
+                $list = $registry->callByPackage('horde', 'admin_list');
+                foreach ($list as $method => $vals) {
+                    $name = Horde::stripAccessKey($vals['name']);
+                    $icon = isset($vals['icon'])
+                        ? Horde_Themes::img($vals['icon'])
+                        : $registry->get('icon');
+
+                    $menu['administration_' . $method] = array(
+                        'name' => $name,
+                        'icon' => strval($icon),
+                        'status' => 'active',
+                        'menu_parent' => 'administration',
+                        'url' => Horde::url($registry->applicationWebPath($vals['link'], 'horde')),
+                    );
+                }
+            } catch (Horde_Exception $e) {}
+        }
+
+        if (Horde_Menu::showService('options') &&
+            ($conf['prefs']['driver'] != '') &&
+            ($conf['prefs']['driver'] != 'none')) {
+            $menu['options'] = array(
+                'name' => _("Options"),
+                'icon' => strval(Horde_Themes::img('prefs.png')),
+                'status' => 'active'
+            );
+
+            /* Get a list of configurable applications. */
+            $prefs_apps = array();
+            foreach ($registry->applications as $application => $params) {
+                if (($params['status'] == 'heading') ||
+                    ($params['status'] == 'block') ||
+                    !file_exists($registry->get('fileroot', $application) . '/config/prefs.php')) {
+                    continue;
+                }
+
+                /* Check if the current user has permission to see this
+                 * application, and if the application is active.
+                 * Administrators always see all applications. */
+                try {
+                    if (($registry->isAdmin() &&
+                         ($params['status'] != 'inactive')) ||
+                        ($registry->hasPermission($application) &&
+                         ($params['status'] == 'active'))) {
+                        $prefs_apps[$application] = _($params['name']);
+                    }
+                } catch (Horde_Exception $e) {
+                    /* @todo Remove or log instead of notifying when all apps
+                     * have been H4-ified. */
+                    $notification->push($e);
+                }
+            }
+
+            if (!empty($prefs_apps['horde'])) {
+                $menu['options_' . 'horde'] = array(
+                    'name' => _("Global Options"),
+                    'status' => 'active',
+                    'menu_parent' => 'options',
+                    'icon' => strval($registry->get('icon', 'horde')),
+                    'url' => strval(Horde::getServiceLink('options', 'horde'))
+                );
+                unset($prefs_apps['horde']);
+            }
+
+            asort($prefs_apps);
+            foreach ($prefs_apps as $app => $name) {
+                $menu['options_' . $app] = array(
+                    'name' => $name,
+                    'status' => 'active',
+                    'menu_parent' => 'options',
+                    'icon' => strval($registry->get('icon', $app)),
+                    'url' => strval(Horde::getServiceLink('options', $app))
+                );
+            }
+        }
+
+        if ($registry->getAuth()) {
+            $menu['logout'] = array(
+                'name' => _("Log out"),
+                'status' => 'active',
+                'icon' => strval(Horde_Themes::img('logout.png')),
+                'url' => Horde::getServiceLink('logout', 'horde'),
+                'target' => '_parent'
+            );
+        } else {
+            $menu['login'] = array(
+                'name' => _("Log in"),
+                'status' => 'active',
+                'icon' => strval(Horde_Themes::img('login.png')),
+                'url' => Horde::getServiceLink('login', 'horde')
+            );
+        }
+
+        // Set up the tree.
+        $tree = $injector->getInstance('Horde_Tree')->getTree('HordeSidebar.tree', 'Javascript');
+
+        foreach ($menu as $app => $params) {
+            if ($params['status'] == 'block') {
+                if ($registry->get('status', $params['app']) == 'inactive') {
+                    continue;
+                }
+
+                try {
+                    $block = Horde_Block_Collection::getBlock($params['app'], $params['blockname']);
+                } catch (Horde_Exception $e) {
+                    Horde::logMessage($e, 'ERR');
+                    continue;
+                }
+
+                try {
+                    $block->buildTree($tree, 0, isset($params['menu_parent']) ? $params['menu_parent'] : null);
+                } catch (Horde_Exception $e) {
+                    Horde::logMessage($e, 'ERR');
+                    continue;
+                }
+            } else {
+                // Need to run the name through gettext since the user's
+                // locale may not have been loaded when registry.php was
+                // parsed.
+                $name = _($params['name']);
+
+                // Headings have no webroot; they're just containers for other
+                // menu items.
+                if (isset($params['url'])) {
+                    $url = $params['url'];
+                } elseif (($params['status'] == 'heading') ||
+                          !isset($params['webroot'])) {
+                    $url = null;
+                } else {
+                    $url = Horde::url($params['webroot'] . '/' . (isset($params['initial_page']) ? $params['initial_page'] : ''));
+                }
+
+                $node_params = array(
+                    'icon' => strval((isset($params['icon']) ? $params['icon'] : $registry->get('icon', $app))),
+                    'icondir' => '',
+                    'target' => isset($params['target']) ? $params['target'] : null,
+                    'url' => $url
+                );
+
+                $tree->addNode($app, empty($params['menu_parent']) ? null : $params['menu_parent'], $name, 0, false, $node_params);
+            }
+        }
+
+        return $tree;
+    }
+
+}
index bed1fb6..6756d94 100644 (file)
  * See the enclosed file COPYING for license information (LGPL). If you
  * did not receive this file, see http://www.fsf.org/copyleft/lgpl.html.
  *
- * @author Michael Pawlowsky <mikep@clearskymedia.ca>
- * @author Chuck Hagenbuch <chuck@horde.org>
+ * @author   Michael Pawlowsky <mikep@clearskymedia.ca>
+ * @author   Chuck Hagenbuch <chuck@horde.org>
+ * @category Horde
+ * @package  Horde
  */
 
-/**
- * Determine if the current user can see an application.
- *
- * @param string $app         The application name.
- * @param array $params       The application's parameters.
- * @param array $hasChildren  Reference to an array to set children flags in.
- */
-function canSee($app, $params, &$hasChildren)
-{
-    global $registry;
-
-    static $cache = array();
-    static $isAdmin;
-    static $user;
-
-    // If we have a cached value for this application, return it now.
-    if (isset($cache[$app])) {
-        return $cache[$app];
-    }
-
-    // Initialize variables we'll keep using in successive calls on
-    // the first call.
-    if (is_null($isAdmin)) {
-        $isAdmin = $registry->isAdmin();
-        $user = $registry->getAuth();
-    }
-
-    // Check if the current user has permisson to see this application, and if
-    // the application is active. Headings are visible to everyone (but get
-    // filtered out later if they have no children). Administrators always see
-    // all applications except those marked 'inactive'. Anyone with SHOW
-    // permissions can see an application, but READ is needed to actually use
-    // the application. You can use this distinction to show applications to
-    // guests that they need to log in to use. If you don't want them to see
-    // apps they can't use, then don't give guests SHOW permissions to
-    // anything.
-    if (// Don't show applications that aren't installed, even if they're
-        // configured.
-        (isset($params['fileroot']) && !is_dir($params['fileroot'])) ||
-
-        // Don't show blocks of applications that aren't installed.
-        ($params['status'] == 'block' &&
-         !is_dir($registry->get('fileroot', $params['app']))) ||
-
-        // Filter out entries that are disabled, hidden or shouldn't show up
-        // in the menu.
-        $params['status'] == 'notoolbar' || $params['status'] == 'hidden' ||
-        $params['status'] == 'inactive') {
-
-        $cache[$app] = false;
-
-    } elseif (// Headings can always be seen.
-              ($params['status'] == 'heading') ||
-
-              // Admins see everything that makes it to this point.
-              ($isAdmin ||
-
-               // Users who have SHOW permissions to active or block entries
-               // see them.
-               ($registry->hasPermission($app, Horde_Perms::SHOW) &&
-                ($params['status'] == 'active' ||
-                 $params['status'] == 'block')))) {
-
-        $cache[$app] = true;
-
-        // Note that the parent node, if any, has children.
-        if (isset($params['menu_parent'])) {
-            $hasChildren[$params['menu_parent']] = true;
-        }
-    } else {
-        // Catch anything that fell through, and don't show it.
-        $cache[$app] = false;
-    }
-
-    return $cache[$app];
-}
-
-/**
- * Builds the menu structure depending on application permissions.
- */
-function buildMenu()
-{
-    global $conf, $registry;
-
-    $apps = array();
-    $children = array();
-    foreach ($registry->applications as $app => $params) {
-        if (canSee((!empty($params['app']) ? $params['app'] : $app), $params, $children)) {
-            $apps[$app] = $params;
-        }
-    }
-
-    $menu = array();
-    foreach ($apps as $app => $params) {
-        // Filter out all headings without children.
-        if ($params['status'] == 'heading' && empty($children[$app])) {
-            continue;
-        }
+require_once dirname(__FILE__) . '/../../lib/Application.php';
+Horde_Registry::appInit('horde', array('authentication' => 'none'));
 
-        $menu[$app] = $params;
-    }
+/* We may not be in global scope since this file can be included from other
+ * scripts. */
+global $conf, $language, $prefs, $registry;
 
-    // Add the administration menu if the user is an admin.
-    if ($registry->isAdmin()) {
-        $menu['administration'] = array('name' => _("Administration"),
-                                        'icon' => (string)Horde_Themes::img('administration.png'),
-                                        'status' => 'heading');
-
-        try {
-            $list = $registry->callByPackage('horde', 'admin_list');
-            foreach ($list as $method => $vals) {
-                $name = Horde::stripAccessKey($vals['name']);
-                $icon = isset($vals['icon'])
-                    ? Horde_Themes::img($vals['icon'])
-                    : $registry->get('icon');
-
-                $menu['administration_' . $method] = array(
-                    'name' => $name,
-                    'icon' => (string)$icon,
-                    'status' => 'active',
-                    'menu_parent' => 'administration',
-                    'url' => Horde::url($registry->applicationWebPath($vals['link'], 'horde')),
-                    );
-            }
-        } catch (Horde_Exception $e) {}
-    }
-
-    if (Horde_Menu::showService('options') &&
-        $conf['prefs']['driver'] != '' && $conf['prefs']['driver'] != 'none') {
-        $menu['options'] = array('name' => _("Options"),
-                                 'status' => 'active',
-                                 'icon' => (string)Horde_Themes::img('prefs.png'));
-
-        /* Get a list of configurable applications. */
-        $prefs_apps = array();
-        foreach ($registry->applications as $application => $params) {
-            if ($params['status'] == 'heading' ||
-                $params['status'] == 'block' ||
-                !file_exists($registry->get('fileroot', $application) . '/config/prefs.php')) {
-                continue;
-            }
-
-            /* Check if the current user has permission to see this
-             * application, and if the application is active.
-             * Administrators always see all applications. */
-            try {
-                if (($registry->isAdmin() && $params['status'] != 'inactive') ||
-                    ($registry->hasPermission($application) &&
-                     ($params['status'] == 'active'))) {
-                    $prefs_apps[$application] = _($params['name']);
-                }
-            } catch (Horde_Exception $e) {
-                // @todo Remove or log instead of notifying when all apps have
-                // been H4-ified.
-                $GLOBALS['notification']->push($e);
-            }
-        }
-
-        if (!empty($prefs_apps['horde'])) {
-            $menu['options_' . 'horde'] = array('name' => _("Global Options"),
-                                                'status' => 'active',
-                                                'menu_parent' => 'options',
-                                                'icon' => (string)$registry->get('icon', 'horde'),
-                                                'url' => Horde::url($registry->get('webroot', 'horde') . '/services/prefs.php?app=horde'));
-            unset($prefs_apps['horde']);
-        }
-
-        asort($prefs_apps);
-        foreach ($prefs_apps as $app => $name) {
-            $menu['options_' . $app] = array('name' => $name,
-                                             'status' => 'active',
-                                             'menu_parent' => 'options',
-                                             'icon' => (string)$registry->get('icon', $app),
-                                             'url' => Horde::url($registry->get('webroot', 'horde') . '/services/prefs.php?app=' . $app));
-        }
-    }
-
-    if ($registry->getAuth()) {
-        $menu['logout'] = array('name' => _("Log out"),
-                                'status' => 'active',
-                                'icon' => (string)Horde_Themes::img('logout.png'),
-                                'url' => Horde::getServiceLink('logout', 'horde'),
-                                'target' => '_parent');
-    } else {
-        $menu['login'] = array('name' => _("Log in"),
-                               'status' => 'active',
-                               'icon' => (string)Horde_Themes::img('login.png'),
-                               'url' => Horde::getServiceLink('login', 'horde'));
-    }
-
-    return $menu;
-}
-
-function sidebar()
-{
-    global $registry, $conf, $language, $prefs;
-
-    // Set up the tree.
-    $tree = $GLOBALS['injector']->getInstance('Horde_Tree')->getTree('horde_menu', 'Javascript');
-    $menu = buildMenu();
-    foreach ($menu as $app => $params) {
-        if ($params['status'] == 'block') {
-            if ($registry->get('status', $params['app']) == 'inactive') {
-                continue;
-            }
+if (!Horde_Util::getFormData('ajaxui') &&
+    ($conf['menu']['always'] ||
+     ($registry->getAuth() && $prefs->getValue('show_sidebar')))) {
+    $sidebar = new Horde_Ui_Sidebar();
+    $tree = $sidebar->getTree();
 
-            try {
-                $block = Horde_Block_Collection::getBlock($params['app'], $params['blockname']);
-            } catch (Horde_Exception $e) {
-                Horde::logMessage($e, 'ERR');
-                continue;
-            }
+    Horde::addScriptFile('prototype.js', 'horde');
+    Horde::addScriptFile('sidebar.js', 'horde');
 
-            try {
-                $block->buildTree($tree, 0, isset($params['menu_parent']) ? $params['menu_parent'] : null);
-            } catch (Horde_Exception $e) {
-                Horde::logMessage($e, 'ERR');
-                continue;
-            }
-        } else {
-            // Need to run the name through gettext since the user's
-            // locale may not have been loaded when registry.php was
-            // parsed.
-            $name = _($params['name']);
+    $ajax_url = Horde::getServiceLink('ajax', 'horde');
+    $ajax_url->pathInfo = 'sidebarUpdate';
 
-            // Headings have no webroot; they're just containers for other
-            // menu items.
-            if (isset($params['url'])) {
-                $url = $params['url'];
-            } elseif ($params['status'] == 'heading' || !isset($params['webroot'])) {
-                $url = null;
-            } else {
-                $url = Horde::url($params['webroot'] . '/' . (isset($params['initial_page']) ? $params['initial_page'] : ''));
-            }
+    $charset = $registry->getCharset();
 
-            $node_params = array('url' => $url,
-                                 'target' => isset($params['target']) ? $params['target'] : null,
-                                 'icon' => (string)(isset($params['icon']) ? $params['icon'] : $registry->get('icon', $app)),
-                                 'icondir' => '',
-                                 );
-            $tree->addNode($app, !empty($params['menu_parent']) ? $params['menu_parent'] : null, $name, 0, false, $node_params);
-        }
-    }
+    Horde::addInlineScript(array(
+        'HordeSidebar.domain = ' . Horde_Serialize::serialize($conf['cookie']['domain'], Horde_Serialize::JSON, $charset),
+        'HordeSidebar.path = ' . Horde_Serialize::serialize($conf['cookie']['path'], Horde_Serialize::JSON, $charset),
+        'HordeSidebar.refresh = ' . intval($prefs->getValue('menu_refresh_time')),
+        'HordeSidebar.rtl = ' . intval(isset($registry->nlsconfig['rtl'][$language])),
+        'HordeSidebar.url = ' . Horde_Serialize::serialize(strval($ajax_url), Horde_Serialize::JSON, $charset),
+        'HordeSidebar.width = ' . intval($prefs->getValue('sidebar_width'))
+    ));
 
-    // If we're serving a request to the JS update client, just render the
-    // updated node javascript.
-    if (Horde_Util::getFormData('httpclient')) {
-        header('Content-Type: application/json; charset=' . $GLOBALS['registry']->getCharset());
-        $scripts = array(
-            $tree->renderNodeDefinitions(),
-            '$(\'horde_menu\').setStyle({ width: \'auto\', height: \'auto\' });');
-        echo Horde::wrapInlineScript($scripts);
-        exit;
-    }
+    require $registry->get('templates', 'horde') . '/portal/sidebar.inc';
 
-    $rtl = isset($GLOBALS['registry']->nlsconfig['rtl'][$language]);
-    Horde::addScriptFile('prototype.js', 'horde');
-    Horde::addScriptFile('sidebar.js', 'horde');
-    require $GLOBALS['registry']->get('templates', 'horde') . '/portal/sidebar.inc';
-}
-
-if (!empty($_GET['httpclient'])) {
-    require_once dirname(__FILE__) . '/../../lib/Application.php';
-    Horde_Registry::appInit('horde', array('authentication' => 'none'));
-}
-
-if (!Horde_Util::getFormData('ajaxui') &&
-    ($GLOBALS['conf']['menu']['always'] ||
-     ($GLOBALS['registry']->getAuth() &&
-      $GLOBALS['prefs']->getValue('show_sidebar')))) {
-    sidebar();
-    echo '<div class="body" style="margin-left:' . $GLOBALS['prefs']->getValue('sidebar_width') . 'px">';
+    echo '<div id="horde_body" class="body" style="margin-left:' . intval($prefs->getValue('sidebar_width')) . 'px">';
 } else {
     echo '<div class="body">';
 }
index 8930cd6..abdb1d9 100644 (file)
@@ -1,23 +1,12 @@
-<div class="sidebar" style="width:<?php echo (isset($prefs) ? $prefs->getValue('sidebar_width') : 150) ?>px">
-
-<div id="expandedSidebar" style="overflow:hidden">
<span id="expandButton" class="rightFloat"><?php echo Horde::link('#', _("Collapse Sidebar"), '', '', 'HordeSidebar.toggleMenuFrame(); return false;', _("Collapse Sidebar")) . Horde::img('hide_panel.png') . '</a>' ?></span>
<div id="sidebarPanel">
-  <?php $tree->renderTree() ?>
+<div class="sidebar" style="width:<?php echo $prefs->getValue('sidebar_width') ?>px">
+ <div id="expandedSidebar" style="overflow:hidden">
+  <span id="expandButton" class="rightFloat"><?php echo Horde::img('hide_panel.png', null, array('title' => _("Collapse Sidebar"))) ?></span>
 <div id="sidebarPanel">
  <?php $tree->renderTree() ?>
+  </div>
  </div>
-</div>
-
-<div id="hiddenSidebar">
- <?php echo Horde::link('#', '', '', '', 'HordeSidebar.toggleMenuFrame(); return false;') . Horde::img('show_panel.png') . '</a>' ?>
-</div>
-
-<script type="text/javascript">
-var horde_sidebar_rtl = <?php echo $rtl ? 'true' : 'false' ?>,
-    horde_sidebar_cols = <?php echo (isset($prefs) ? $prefs->getValue('sidebar_width') : 150) ?>,
-    horde_sidebar_domain = '<?php echo htmlspecialchars($GLOBALS['conf']['cookie']['domain']) ?>',
-    horde_sidebar_path = '<?php echo $GLOBALS['conf']['cookie']['path'] ?>',
-    horde_sidebar_refresh = <?php echo intval($prefs->getValue('menu_refresh_time')) ?>,
-    horde_sidebar_url = '<?php echo Horde::url($GLOBALS['registry']->get('webroot', 'horde') . '/services/portal/sidebar.php') ?>';
-</script>
 
+ <div id="hiddenSidebar">
+  <?php echo Horde::img('show_panel.png') ?>
+ </div>
 </div>