More refactoring of Ansel_View
authorMichael J. Rubinsky <mrubinsk@horde.org>
Fri, 31 Jul 2009 15:52:23 +0000 (11:52 -0400)
committerMichael J. Rubinsky <mrubinsk@horde.org>
Fri, 31 Jul 2009 15:52:23 +0000 (11:52 -0400)
Get rid of makeView() method, replace with an actual const'r, rename
classes more appropriately.

ansel/lib/View/Abstract.php
ansel/lib/View/Base.php [new file with mode: 0644]
ansel/lib/View/Gallery.php
ansel/lib/View/Image.php
ansel/lib/View/List.php
ansel/view.php

index acbf521..bcd1bb7 100644 (file)
@@ -6,16 +6,16 @@
  * @author  Michael J. Rubinsky <mrubinsk@horde.org>
  * @package Ansel
  */
-class Ansel_View_Abstract {
-
-    var $_params = array();
+class Ansel_View_Base
+{
+    protected $_params = array();
 
     /**
      * The ansel resource this view is for.
      *
      * @var mixed  Either an Ansel_Gallery or Ansel_Image
      */
-    var $resource;
+    public $resource;
 
     /**
      * The gallery object (will be eq to $resource in a gallery view
diff --git a/ansel/lib/View/Base.php b/ansel/lib/View/Base.php
new file mode 100644 (file)
index 0000000..6c39d22
--- /dev/null
@@ -0,0 +1,198 @@
+<?php
+/**
+ * The Ansel_View_Abstract:: Parent class for the various Ansel_View classes
+ *
+ * @author  Chuck Hagenbuch <chuck@horde.org>
+ * @author  Michael J. Rubinsky <mrubinsk@horde.org>
+ * @package Ansel
+ */
+abstract class Ansel_View_Base
+{
+    protected $_params = array();
+
+    /**
+     * The ansel resource this view is for.
+     *
+     * @var mixed  Either an Ansel_Gallery or Ansel_Image
+     */
+    public $resource;
+
+    /**
+     * The gallery object (will be eq to $resource in a gallery view
+     *
+     * @var Ansel_Gallery
+     */
+    public $gallery;
+
+    /**
+     * Collection of Ansel_Widgets to display in this view.
+     *
+     * @var array
+     */
+    protected $_widgets = array();
+
+
+    public function __construct($params)
+    {
+        $this->_params = $params;
+    }
+
+    public function &getGallery($galleryId = null, $slug = '')
+    {
+        if (is_null($galleryId) && empty($slug)) {
+            $galleryId = !empty($this->_params['gallery_id']) ? $this->_params['gallery_id'] : null;
+            $slug = !empty($this->_params['gallery_slug']) ? $this->_params['gallery_slug'] : null;
+        }
+
+        if (empty($galleryId) && empty($slug)) {
+            return PEAR::raiseError(_("No gallery specified"));
+        }
+
+        // If we have a slug, use it.
+        if (!empty($slug)) {
+            $gallery = &$GLOBALS['ansel_storage']->getGalleryBySlug($slug);
+        } else {
+            $gallery = &$GLOBALS['ansel_storage']->getGallery($galleryId);
+        }
+        if (is_a($gallery, 'PEAR_Error')) {
+            return $gallery;
+        } elseif (!$gallery->hasPermission(Horde_Auth::getAuth(), PERMS_READ)) {
+            return PEAR::raiseError(sprintf(_("Access denied to gallery \"%s\"."), $gallery->get('name')));
+        }
+
+        /* Set any date info we might have */
+        if (!empty($this->_params['year'])) {
+            $date = Ansel::getDateParameter(
+                array('year' => $this->_params['year'],
+                      'month' => $this->_params['month'],
+                      'day' => $this->_params['day']));
+        } else {
+            $date = array();
+        }
+        $gallery->setDate($date);
+
+        return $gallery;
+    }
+
+    /**
+     * Add an Ansel_Widget to be displayed in this view.
+     *
+     * @param Ansel_Widget $widget  The Ansel_Widget to display
+     */
+    public function addWidget($widget)
+    {
+        $result = $widget->attach($this);
+        if (!empty($result)) {
+            $this->_widgets[] = $widget;
+        }
+    }
+
+
+    /**
+     * Output any widgets associated with this view.
+     *
+     */
+    public function renderWidgets()
+    {
+        $this->_renderWidgets();
+    }
+
+    /**
+     * Count the number of widgets we have attached.
+     *
+     * @return integer  The number of widgets attached to this view.
+     */
+    public function countWidgets()
+    {
+        return count($this->_widgets);
+    }
+
+    /**
+     * Default widget rendering, can be overridden by any subclass.
+     *
+     */
+    protected function _renderWidgets()
+    {
+        echo '<div class="anselWidgets">';
+        foreach ($this->_widgets as $widget) {
+            if ($widget->autoRender) {
+                echo $widget->html();
+                echo '<br />';
+            }
+        }
+        echo '</div>';
+    }
+
+   /**
+     * JSON representation of this gallery's images.
+     *
+     * @param array $images   An array of Ansel_Image objects. If this is null
+     *                        the images are fetched based on $from and $count.
+     *
+     * @param integer $from   Image to start at.
+     * @param integer $count  Number of images to get.
+     *
+     * @return string  A serialized JSON array.
+     */
+    public function json($images = null, $full = false, $from = 0, $count = 0,
+                         $image_view = 'screen', $view_links = false)
+    {
+        global $conf, $prefs;
+
+        $json = array();
+        $perpage = $prefs->getValue('tilesperpage', $conf['thumbnail']['perpage']);
+        $curimage = 0;
+        $curpage =  0;
+
+        if (is_null($images)) {
+            $images = $this->gallery->getImages($from, $count);
+        }
+
+        $style = $this->gallery->getStyle();
+
+        foreach ($images as $image) {
+            // Calculate the page this image will appear on in the
+            // gallery view.
+            if (++$curimage > $perpage) {
+                ++$curpage;
+                $curimage = 0;
+            }
+
+            $data = array(Ansel::getImageUrl($image->id, $image_view, $full, $style['name']),
+                          htmlspecialchars($image->filename, ENT_COMPAT, Horde_Nls::getCharset()),
+                          Horde_Text_Filter::filter($image->caption, 'text2html', array('parselevel' => Horde_Text_Filter_Text2html::MICRO_LINKURL)),
+                          $image->id,
+                          $curpage);
+            if ($view_links) {
+                $data[] = Ansel::getUrlFor('view',
+                    array('gallery' => $this->gallery->id,
+                          'slug' => $this->gallery->get('slug'),
+                          'image' => $image->id,
+                          'view' => 'Image'),
+                    true);
+                $data[] = Ansel::getUrlFor('view',
+                    array('gallery' => $image->gallery,
+                          'slug' => $this->gallery->get('slug'),
+                          'view' => 'Gallery'),
+                    true);
+            }
+            // Source, Width, Height, Name, Caption, Image Id, Gallery Page
+            $json[] = $data;
+        }
+
+        return Horde_Serialize::serialize($json, Horde_Serialize::JSON, Horde_Nls::getCharset());
+    }
+
+    /**
+     * @abstract
+     * @return unknown_type
+     */
+    abstract public function viewType();
+
+    abstract public function getGalleryCrumbData();
+
+    abstract public function getTitle();
+
+    abstract public function html();
+
+}
index a08559e..fd8854d 100644 (file)
@@ -1,24 +1,26 @@
 <?php
 /**
- * @package Ansel
- */
-
-/** Ansel_View_Abstract */
-require_once ANSEL_BASE . '/lib/Views/Abstract.php';
-
-/**
  * The Ansel_View_Gallery:: class wraps display of individual images.
  *
+ * See the enclosed file COPYING for license information (GPL). If you
+ * did not receive this file, see http://www.fsf.org/copyleft/gpl.html.
+ *
  * @author  Chuck Hagenbuch <chuck@horde.org>
+ * @author  Michael J. Rubinsky <mrubinsk@horde.org>
+ *
  * @package Ansel
  */
-class Ansel_View_Gallery extends Ansel_View_Abstract {
-
-    /** Holds the object that does the actual rendering **/
-    var $_renderer;
+class Ansel_View_Gallery extends Ansel_View_Base
+{
+    /**
+     *  Holds the object that does the actual rendering.
+     *
+     *  @var Ansel_View_GalleryRenderer
+     */
+    protected $_renderer;
 
     /**
-     * @static
+     * Const'r
      *
      * @param array $params  Any parameters that the view might need.
      * <pre>
@@ -67,105 +69,92 @@ class Ansel_View_Gallery extends Ansel_View_Abstract {
      *                         with more then one resource. Used from the api
      *                         when clicking on breadcrumb links, for example.
      * </pre>
-     *
-     * @TODO use exceptions from the constructor instead of static
-     * instance-getting.
      */
-    function makeView($params = array())
+    public function makeView($params = array())
     {
-        $view = new Ansel_View_Gallery();
-
-        if (count($params)) {
-            $view->_params = $params;
-        }
+        parent::__construct($params);
 
         if (!empty($params['gallery_slug'])) {
-            $view->gallery = $view->getGallery(null, $params['gallery_slug']);
+            $this->gallery = $this->getGallery(null, $params['gallery_slug']);
         } elseif (!empty($params['gallery_id'])) {
-            $view->gallery = $view->getGallery($params['gallery_id']);
+            $this->gallery = $this->getGallery($params['gallery_id']);
         } else {
-            $view->gallery = $view->getGallery();
-        }
-
-        if (is_a($view->gallery, 'PEAR_Error')) {
-            return $view->gallery;
+            $this->gallery = $this->getGallery();
         }
 
         // Check user age
-        if (!$view->gallery->isOldEnough()) {
+        if (!$this->gallery->isOldEnough()) {
             if (!empty($params['api'])) {
-                return PEAR::raiseError(_("Locked galleries are not viewable via the api."));
+                throw new Horde_Exception('Locked galleries are not viewable via the api.');
             }
             $date = Ansel::getDateParameter(
-                array('year' => isset($view->_params['year']) ? $view->_params['year'] : 0,
-                      'month' => isset($view->_params['month']) ? $view->_params['month'] : 0,
-                      'day' => isset($view->_params['day']) ? $view->_params['day'] : 0));
+                array('year' => isset($this->_params['year']) ? $this->_params['year'] : 0,
+                      'month' => isset($this->_params['month']) ? $this->_params['month'] : 0,
+                      'day' => isset($this->_params['day']) ? $this->_params['day'] : 0));
 
                 $galleryurl = Ansel::getUrlFor('view', array_merge(
-                                   array('gallery' => $view->gallery->id,
+                                   array('gallery' => $this->gallery->id,
                                          'slug' => empty($params['slug']) ? '' : $params['slug'],
                                          'page' => empty($params['page']) ? 0 : $params['page'],
                                          'view' => 'Gallery'),
                                    $date),
                                    true);
 
-            $params = array('gallery' => $view->gallery->id, 'url' => $galleryurl);
+            $params = array('gallery' => $this->gallery->id, 'url' => $galleryurl);
             header('Location: ' . Horde_Util::addParameter(Horde::applicationUrl('disclamer.php'), $params, null, false));
             exit;
         }
 
-        if ($view->gallery->hasPasswd()) {
+        if ($this->gallery->hasPasswd()) {
             if (!empty($params['api'])) {
                 return PEAR::raiseError(_("Locked galleries are not viewable via the api."));
             }
             $date = Ansel::getDateParameter(
-                array('year' => isset($view->_params['year']) ? $view->_params['year'] : 0,
-                      'month' => isset($view->_params['month']) ? $view->_params['month'] : 0,
-                      'day' => isset($view->_params['day']) ? $view->_params['day'] : 0));
+                array('year' => isset($this->_params['year']) ? $this->_params['year'] : 0,
+                      'month' => isset($this->_params['month']) ? $this->_params['month'] : 0,
+                      'day' => isset($this->_params['day']) ? $this->_params['day'] : 0));
 
                 $galleryurl = Ansel::getUrlFor('view', array_merge(
-                                   array('gallery' => $view->gallery->id,
+                                   array('gallery' => $this->gallery->id,
                                          'slug' => empty($params['slug']) ? '' : $params['slug'],
                                          'page' => empty($params['page']) ? 0 : $params['page'],
                                          'view' => 'Gallery'),
                                    $date),
                                    true);
 
-            $params = array('gallery' => $view->gallery->id, 'url' => $galleryurl);
+            $params = array('gallery' => $this->gallery->id, 'url' => $galleryurl);
             header('Location: ' . Horde_Util::addParameter(Horde::applicationUrl('protect.php'), $params, null, false));
             exit;
         }
 
-        if (!$view->gallery->hasPermission(Horde_Auth::getAuth(), PERMS_READ)) {
-            return PEAR::raiseError(_("Access denied viewing this gallery."));
+        if (!$this->gallery->hasPermission(Horde_Auth::getAuth(), PERMS_READ)) {
+            throw new Horde_Exception('Access denied viewing this gallery.');
         }
 
         // Since this is a gallery view, the resource is just a reference to the
         // gallery. We keep both instance variables becuase both gallery and
         // image views are assumed to have a gallery object.
-        $view->resource = &$view->gallery;
+        $this->resource = &$this->gallery;
 
         /* Do we have an explicit style set? If not, use the gallery's */
-        if (!empty($view->_params['style'])) {
-            $style = Ansel::getStyleDefinition($view->_params['style']);
+        if (!empty($this->_params['style'])) {
+            $style = Ansel::getStyleDefinition($this->_params['style']);
         } else {
-            $style = $view->gallery->getStyle();
+            $style = $this->gallery->getStyle();
         }
 
-        if (!empty($view->_params['gallery_view'])) {
-            $renderer = $view->_params['gallery_view'];
+        if (!empty($this->_params['gallery_view'])) {
+            $renderer = $this->_params['gallery_view'];
         } else {
             $renderer = (!empty($style['gallery_view'])) ? $style['gallery_view'] : 'Gallery';
         }
         /* Load the helper */
         $classname = 'Ansel_View_GalleryRenderer_' . basename($renderer);
-        $view->_renderer = new $classname($view);
-        $view->_renderer->init();
-
-        return $view;
+        $this->_renderer = new $classname($this);
+        $this->_renderer->init();
     }
 
-    function getGalleryCrumbData()
+    public function getGalleryCrumbData()
     {
         return $this->gallery->getGalleryCrumbData();
     }
@@ -175,7 +164,7 @@ class Ansel_View_Gallery extends Ansel_View_Abstract {
      *
      * @return string  The gallery's title.
      */
-    function getTitle()
+    public function getTitle()
     {
         if (is_a($this->gallery, 'PEAR_Error')) {
             return $this->gallery->getMessage();
@@ -189,12 +178,12 @@ class Ansel_View_Gallery extends Ansel_View_Abstract {
      * @return string  The HTML.
      *
      */
-    function html()
+    public function html()
     {
         return $this->_renderer->html();
     }
 
-    function viewType()
+    public function viewType()
     {
         return 'Gallery';
     }
index 69a1168..1ae9e4e 100644 (file)
@@ -2,66 +2,55 @@
 /**
  * The Ansel_View_Image:: class wraps display of individual images.
  *
+ * See the enclosed file COPYING for license information (GPL). If you
+ * did not receive this file, see http://www.fsf.org/copyleft/gpl.html.
+ *
  * @author  Chuck Hagenbuch <chuck@horde.org>
+ * @author  Michael J. Rubinsky <mrubinsk@horde.org>
+ *
  * @package Ansel
  */
-
-/** Ansel_View_Abstract */
-require_once ANSEL_BASE . '/lib/Views/Abstract.php';
-
-class Ansel_View_Image extends Ansel_View_Abstract {
-
+class Ansel_View_Image extends Ansel_View_Base
+{
     /**
      *  The image selected for this view.
      *
      * @var Ansel_Image
      */
-    var $image;
+    //public $image;
 
     /**
-     * @static
+     * Const'r
      *
-     * @TODO use exceptions from the constructor instead of static
-     * instance-getting.
      */
-    function makeView($params = array())
+    public function __construct($params = array())
     {
+        parent::__construct();
+
         /* Get the image */
         $image_id = $params['image_id'];
 
+        /* Get the Ansel_Image */
         $image = &$GLOBALS['ansel_storage']->getImage($image_id);
-        if (is_a($image, 'PEAR_Error')) {
-            return $image;
-        }
 
-        /* Create the Ansel_View object */
-        $view = new Ansel_View_Image;
-
-        /* Save params */
-        if (count($params)) {
-            $view->_params = $params;
-        }
-
-        $view->gallery = $view->getGallery();
-        if (is_a($view->gallery, 'PEAR_Error')) {
-            return $view->gallery;
-        }
+        /* Get the Ansel_Gallery */
+        $this->gallery = $view->getGallery();
 
         /* Save the image reference */
-        $view->resource = $image;
+        $this->resource = $image;
 
-        // Check user age
-        if (!$view->gallery->isOldEnough()) {
+        /* Check user age */
+        if (!$this->gallery->isOldEnough()) {
             if (!empty($params['api'])) {
-                return PEAR::raiseError(_("Locked galleries are not viewable via the api."));
+               throw new Horde_Exception('Locked galleries are not viewable via the api.');
             }
             $date = Ansel::getDateParameter(
-                array('year' => isset($view->_params['year']) ? $view->_params['year'] : 0,
-                      'month' => isset($view->_params['month']) ? $view->_params['month'] : 0,
-                      'day' => isset($view->_params['day']) ? $view->_params['day'] : 0));
+                array('year' => isset($this->_params['year']) ? $this->_params['year'] : 0,
+                      'month' => isset($this->_params['month']) ? $this->_params['month'] : 0,
+                      'day' => isset($this->_params['day']) ? $this->_params['day'] : 0));
 
                 $url = Ansel::getUrlFor('view', array_merge(
-                    array('gallery' => $view->gallery->id,
+                    array('gallery' => $this->gallery->id,
                           'slug' => empty($params['slug']) ? '' : $params['slug'],
                           'page' => empty($params['page']) ? 0 : $params['page'],
                           'view' => 'Image',
@@ -69,24 +58,24 @@ class Ansel_View_Image extends Ansel_View_Abstract {
                     $date),
                     true);
 
-            $params = array('gallery' => $view->gallery->id, 'url' => $url);
+            $params = array('gallery' => $this->gallery->id, 'url' => $url);
 
             header('Location: ' . Horde_Util::addParameter(Horde::applicationUrl('disclamer.php'), $params, null, false));
             exit;
         }
 
         // Check password
-        if ($view->gallery->hasPasswd()) {
+        if ($this->gallery->hasPasswd()) {
             if (!empty($params['api'])) {
                 return PEAR::raiseError(_("Locked galleries are not viewable via the api."));
             }
             $date = Ansel::getDateParameter(
-                array('year' => isset($view->_params['year']) ? $view->_params['year'] : 0,
-                      'month' => isset($view->_params['month']) ? $view->_params['month'] : 0,
-                      'day' => isset($view->_params['day']) ? $view->_params['day'] : 0));
+                array('year' => isset($this->_params['year']) ? $this->_params['year'] : 0,
+                      'month' => isset($this->_params['month']) ? $this->_params['month'] : 0,
+                      'day' => isset($this->_params['day']) ? $this->_params['day'] : 0));
 
                 $url = Ansel::getUrlFor('view', array_merge(
-                    array('gallery' => $view->gallery->id,
+                    array('gallery' => $this->gallery->id,
                           'slug' => empty($params['slug']) ? '' : $params['slug'],
                           'page' => empty($params['page']) ? 0 : $params['page'],
                           'view' => 'Image',
@@ -94,7 +83,7 @@ class Ansel_View_Image extends Ansel_View_Abstract {
                     $date),
                     true);
 
-            $params = array('gallery' => $view->gallery->id, 'url' => $url);
+            $params = array('gallery' => $this->gallery->id, 'url' => $url);
 
             header('Location: ' . Horde_Util::addParameter(Horde::applicationUrl('protect.php'), $params, null, false));
             exit;
@@ -102,15 +91,14 @@ class Ansel_View_Image extends Ansel_View_Abstract {
 
 
         /* Any script files we may need if not calling via the api */
-        if (empty($view->_params['api'])) {
+        if (empty($this->_params['api'])) {
             Horde::addScriptFile('effects.js', 'horde', true);
             Horde::addScriptFile('stripe.js', 'horde', true);
         }
 
-        return $view;
     }
 
-    function getGalleryCrumbData()
+    public function getGalleryCrumbData()
     {
         return $this->gallery->getGalleryCrumbData();
     }
@@ -120,7 +108,7 @@ class Ansel_View_Image extends Ansel_View_Abstract {
      *
      * @return string  The title.
      */
-    function getTitle()
+    public function getTitle()
     {
         return $this->resource->filename;
     }
@@ -130,7 +118,7 @@ class Ansel_View_Image extends Ansel_View_Abstract {
      *
      * @return string  The HTML.
      */
-    function html()
+    public function html()
     {
         global $browser, $conf, $prefs, $registry;
 
@@ -381,7 +369,7 @@ class Ansel_View_Image extends Ansel_View_Abstract {
      *
      * @return string  The HTML
      */
-    function _getExifHtml()
+    private function _getExifHtml()
     {
         $data = Ansel_ImageData::getAttributes($this->resource, true);
 
@@ -399,7 +387,7 @@ class Ansel_View_Image extends Ansel_View_Abstract {
         return $html;
     }
 
-    function viewType()
+    public function viewType()
     {
         return 'Image';
     }
index 7882bf2..b6a6c51 100644 (file)
@@ -1,21 +1,18 @@
 <?php
 /**
- * @package Ansel
- */
-
-/** Ansel_View_Abstract */
-require_once ANSEL_BASE . '/lib/Views/Abstract.php';
-
-/**
  * The Ansel_View_Gallery:: class wraps display of individual images.
  *
+ * See the enclosed file COPYING for license information (GPL). If you
+ * did not receive this file, see http://www.fsf.org/copyleft/gpl.html.
+ *
  * @author  Michael J. Rubinsky <mrubinsk@horde.org>
  * @package Ansel
  */
-class Ansel_View_List extends Ansel_View_Abstract {
-
+class Ansel_View_List extends Ansel_View_Base
+{
     /**
-     * @static
+     * Const'r - Not much going on here, leave this here for now as a place
+     * to document the additional parameters this View takes.
      *
      * @param array $params  Any parameters that the view might need.
      * <pre>
@@ -32,15 +29,10 @@ class Ansel_View_List extends Ansel_View_Abstract {
      *
      *  pager_url    -  The url for the pager to use see Ansel_Gallery for
      *                  more information on the url parameters.
-     *
-     * @TODO use exceptions from the constructor instead of static
-     * instance-getting.
      */
-    function makeView($params = array())
+    public function __construct($params = array())
     {
-        $view = new Ansel_View_List;
-        $view->_params = $params;
-        return $view;
+        parent::__construct($params);
     }
 
     /**
@@ -48,7 +40,7 @@ class Ansel_View_List extends Ansel_View_Abstract {
      *
      * @return string  The gallery's title.
      */
-    function getTitle()
+    public function getTitle()
     {
         return _("Gallery List");
     }
@@ -59,7 +51,7 @@ class Ansel_View_List extends Ansel_View_Abstract {
      * @return string  The HTML.
      *
      */
-    function html()
+    public function html()
     {
         global $conf, $prefs, $registry, $ansel_storage, $notification;
 
@@ -262,9 +254,19 @@ class Ansel_View_List extends Ansel_View_Abstract {
         return '';
     }
 
-    function viewType()
+    public function viewType()
     {
         return 'List';
     }
 
+    /**
+     * noop
+     *
+     * @see ansel/lib/View/Ansel_View_Base#getGalleryCrumbData()
+     */
+    public function getGalleryCrumbData()
+    {
+        throw new Horde_Exception('Ansel_View_List::getGalleryCrumbData not implemented.');
+    }
+
 }
index 1d7eab1..d041f77 100644 (file)
 require_once dirname(__FILE__) . '/lib/base.php';
 
 $viewname = basename(Horde_Util::getFormData('view', 'Gallery'));
-include_once ANSEL_BASE . '/lib/Views/' . $viewname . '.php';
 $view = 'Ansel_View_' . $viewname;
 if (!$view || !class_exists($view)) {
-    header('HTTP/1.0 404 Not Found');
-    echo 'Not Found';
-    exit;
+    throw new Horde_Exception(sprintf("Could not load class definition of %s", $view));
 }
 
 /*
@@ -36,11 +33,12 @@ $params['gallery_slug'] = Horde_Util::getFormData('slug');
 $params['force_grouping'] = Horde_Util::getFormData('force_grouping');
 $params['image_id'] = Horde_Util::getFormData('image');
 
-$view = call_user_func(array($view, 'makeView'), $params);
-if (is_a($view, 'PEAR_Error')) {
+try {
+    $view = new $view($params);
+} catch (Horde_Exception $e) {
     require ANSEL_TEMPLATES . '/common-header.inc';
     require ANSEL_TEMPLATES . '/menu.inc';
-    echo '<br /><em>' . htmlspecialchars($view->getMessage()) . '</em>';
+    echo '<br /><em>' . htmlspecialchars($e->getMessage()) . '</em>';
     require $registry->get('templates', 'horde') . '/common-footer.inc';
     exit;
 }