=== modified file 'django/core/paginator.py'
--- django/core/paginator.py	2006-12-19 04:35:09 +0000
+++ django/core/paginator.py	2007-07-08 18:45:15 +0000
@@ -15,56 +15,184 @@
     13 records, num_per_page=10, orphans=2 --> pages==2, len(self.get_page(0))==10
     12 records, num_per_page=10, orphans=2 --> pages==1, len(self.get_page(0))==12
     """
-    def __init__(self, query_set, num_per_page, orphans=0):
+    
+    def __init__(self, query_set, num_per_page=10, orphans=0, page=1):
+        """
+        Initialize the ObjectPaginator instance.
+        
+        Parameters::
+         * ``query_set`` -- A QuerySet or sequence of objects to paginate.
+         * ``num_per_page`` -- The number of objects to put on a page.
+                               By default, ``num_per_page`` is 10.
+         * ``orphans`` -- The number of objects to not put by themselves on
+                          the last page.  For example, if ``orphans`` is 2
+                          and the total number of objects would normally
+                          result in two items on the last page, place those
+                          items on the previous page instead of leaving them
+                          "dangling" on the last page.  By default,
+                          ``orphans`` is 0.
+         * ``page`` -- The page number to initialize the ObjectPaginator
+                       instance to.  ``page`` is 1 by default, meaning that
+                       the ObjectPaginator instance will start on the first
+                       page.  ``page`` may be an integer or the string
+                       representation of an interger, which is useful when
+                       passing directly from a URL query string.
+        """
         self.query_set = query_set
         self.num_per_page = num_per_page
         self.orphans = orphans
-        self._hits = self._pages = None
-
+        self.page = page
+    
+    def _get_query_set(self):
+        """
+        Get the QuerySet or sequence of objects.
+        """
+        return self._query_set
+    
+    def _set_query_set(self, query_set):
+        """
+        Set the QuerySet or sequence of objects and clear the hits cache.
+        """
+        self._hits = None
+        self._query_set = query_set
+    
+    query_set = property(_get_query_set, _set_query_set)
+    
     def validate_page_number(self, page_number):
+        """
+        Coerce the passed page_number to an integer and insure that the
+        page exists.  Return the integer page number.
+        """
         try:
             page_number = int(page_number)
         except ValueError:
             raise InvalidPage
-        if page_number < 0 or page_number > self.pages - 1:
+        if not self.has_page(page_number):
             raise InvalidPage
         return page_number
-
-    def get_page(self, page_number):
+    
+    def _get_page(self):
+        """
+        Get the current page.
+        """
+        return self._page
+        
+    def _set_page(self, page_number):
+        """
+        Set the current page to the passed (1-based) page_number.
+        Raise an InvalidPage exception if page_number is invalid.
+        """
         page_number = self.validate_page_number(page_number)
-        bottom = page_number * self.num_per_page
-        top = bottom + self.num_per_page
-        if top + self.orphans >= self.hits:
-            top = self.hits
-        return self.query_set[bottom:top]
-
+        self._page = page_number
+    
+    page = property(_get_page, _set_page)
+    
+    def _get_first_page(self):
+        """
+        Return the (1-based) page number of the first page.
+        """
+        return 1
+    
+    first_page = property(_get_first_page)
+    
+    def _get_last_page(self):
+        """
+        Return the (1-based) page number of the last page.
+        """
+        return self.pages
+    
+    last_page = property(_get_last_page)        
+    
+    def _get_pages(self):
+        """
+        Return the total number of pages.
+        """
+        hits = max(self.hits - self.orphans - 1, 0)
+        return hits // self.num_per_page + 1
+    
+    pages = property(_get_pages)
+    
+    def has_page(self, page_number):
+        """
+        Return true if the paginator has the passed page_number, and False
+        otherwise.
+        """
+        return self.first_page <= page_number <= self.last_page
+    
+    def next_page(self, page_number=None):
+        """
+        Return the page number of the page after the passed page_number.
+        If page_number is not given, then use the current page.
+        If there is no next page, then return None.
+        """
+        if page_number is None:
+            page_number = self.page
+        else:
+            page_number = self.validate_page_number(page_number)
+        next_page = self.page + 1
+        if self.has_page(next_page):
+            return next_page
+    
     def has_next_page(self, page_number):
-        "Does page $page_number have a 'next' page?"
-        return page_number < self.pages - 1
-
+        """
+        Return True if the passed page_number has a next page, and False
+        otherwise.  If page_number is not given, then use the current page.
+        """
+        return self.next_page(page_number) is not None
+    
+    def previous_page(self, page_number=None):
+        """
+        Return the page number of the page before the passed page_number.
+        If page_number is not given, then use the current page.
+        If there is no previous page, then return None.
+        """
+        if page_number is None:
+            page_number = self.page
+        else:
+            page_number = self.validate_page_number(page_number)
+        previous_page = self.page - 1
+        if self.has_page(previous_page):
+            return previous_page
+    
     def has_previous_page(self, page_number):
-        return page_number > 0
-
-    def first_on_page(self, page_number):
+        """
+        Return True if the passed page_number has a previous page, and False
+        otherwise.  If page_number is not given, then use the current page.
+        """
+        return self.previous_page(page_number) is not None
+    
+    def first_on_page(self, page_number=None):
         """
         Returns the 1-based index of the first object on the given page,
         relative to total objects found (hits).
         """
-        page_number = self.validate_page_number(page_number)
-        return (self.num_per_page * page_number) + 1
-
-    def last_on_page(self, page_number):
+        if page_number is None:
+            page_number = self.page
+        else:
+            page_number = self.validate_page_number(page_number)
+        return (page_number - 1) * self.num_per_page + 1
+    
+    def last_on_page(self, page_number=None):
         """
         Returns the 1-based index of the last object on the given page,
         relative to total objects found (hits).
         """
-        page_number = self.validate_page_number(page_number)
-        page_number += 1   # 1-base
-        if page_number == self.pages:
+        if page_number is None:
+            page_number = self.page
+        else:
+            page_number = self.validate_page_number(page_number)
+        # Last page is special because it can have orphans.
+        if page_number is self.last_page:
             return self.hits
         return page_number * self.num_per_page
 
     def _get_hits(self):
+        """
+        Return the number of objects in the paginator's QuerySet or sequence
+        of objects.  First try to call .count() on self.query_set since
+        this will usually be an actual QuerySet.  If that fails, then fall
+        back to calling len(self.query_set).
+        """
         if self._hits is None:
             # Try .count() or fall back to len().
             try:
@@ -76,13 +204,28 @@
                 self._hits = len(self.query_set)
         return self._hits
 
-    def _get_pages(self):
-        if self._pages is None:
-            hits = (self.hits - 1 - self.orphans)
-            if hits < 1:
-                hits = 0
-            self._pages = hits // self.num_per_page + 1
-        return self._pages
-
     hits = property(_get_hits)
-    pages = property(_get_pages)
+
+    def get_items(self, page_number=None):
+        """
+        Return the slice of items for the passed (1-based) page_number.
+        If page_number is not given, then use the current page.
+        """
+        if page_number is None:
+            page_number = self.page
+        else:
+            page_number = self.validate_page_number(page_number)
+        bottom = (page_number - 1)* self.num_per_page
+        # Special handling of orphans on the last page.
+        if page_number is self.last_page:
+            top = self.hits
+        else:
+            top = bottom + self.num_per_page
+        return self.query_set[bottom:top]
+    
+    def get_page(self, page_number):
+        """
+        This function was kept to keep backwards compatibility.
+        Return the slice of items for the passed (0-based) page_number.
+        """
+        return self.get_items(page_number + 1)

