KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > com > jsptags > navigation > pager > PagerTag


1 /*
2  * Pager Tag Library
3  *
4  * Copyright (C) 2002 James Klicman <james@jsptags.com>
5  *
6  * This library is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU Lesser General Public
8  * License as published by the Free Software Foundation; either
9  * version 2.1 of the License, or (at your option) any later version.
10  *
11  * This library is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14  * Lesser General Public License for more details.
15  *
16  * You should have received a copy of the GNU Lesser General Public
17  * License along with this library; if not, write to the Free Software
18  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
19  */

20
21 package com.jsptags.navigation.pager;
22
23 import javax.servlet.*;
24 import javax.servlet.http.*;
25 import javax.servlet.jsp.*;
26 import javax.servlet.jsp.tagext.*;
27 import java.io.IOException JavaDoc;
28 import com.jsptags.navigation.pager.parser.*;
29
30 public final class PagerTag extends TagSupport {
31
32     static final String JavaDoc
33         DEFAULT_ID = "pager";
34
35     private static final int
36         DEFAULT_MAX_ITEMS = Integer.MAX_VALUE,
37         DEFAULT_MAX_PAGE_ITEMS = 10,
38         DEFAULT_MAX_INDEX_PAGES = 10;
39
40     static final String JavaDoc
41         OFFSET_PARAM = ".offset";
42
43     static final String JavaDoc
44         // scope values
45
PAGE = "page",
46         REQUEST = "request",
47         // index values
48
CENTER = "center",
49         FORWARD = "forward",
50         HALF_FULL = "half-full";
51
52     /*
53      * Tag Properties
54      */

55     private String JavaDoc url = null;
56     private String JavaDoc index = null;
57     private int items = 0;
58     private int maxItems = DEFAULT_MAX_ITEMS;
59     private int maxPageItems = DEFAULT_MAX_PAGE_ITEMS;
60     private int maxIndexPages = DEFAULT_MAX_INDEX_PAGES;
61     private boolean isOffset = false;
62     private String JavaDoc export = null;
63     private String JavaDoc scope = null;
64
65     /*
66      * Tag Variables
67      */

68     private StringBuffer JavaDoc uri = null;
69     private int params = 0;
70     private int offset = 0;
71     private int itemCount = 0;
72     private int pageNumber = 0;
73     private Integer JavaDoc pageNumberInteger = null;
74
75     private String JavaDoc idOffsetParam = DEFAULT_ID+OFFSET_PARAM;
76     private PagerTagExport pagerTagExport = null;
77     private Object JavaDoc oldPager = null;
78     private Object JavaDoc oldOffset = null;
79     private Object JavaDoc oldPageNumber = null;
80
81
82     public PagerTag() {
83         id = DEFAULT_ID;
84     }
85
86     public final void setId(String JavaDoc sid) {
87         super.setId(sid);
88         idOffsetParam = sid+OFFSET_PARAM;
89     }
90
91     public final void setUrl(String JavaDoc value) {
92         url = value;
93     }
94
95     public final String JavaDoc getUrl() {
96         return url;
97     }
98
99
100     public final void setIndex(String JavaDoc val) throws JspException {
101         if (!(val == null ||
102               CENTER.equals(val) ||
103               FORWARD.equals(val) ||
104               HALF_FULL.equals(val)))
105         {
106             throw new JspTagException("value for attribute \"index\" " +
107                 "must be either \"center\", \"forward\" or \"half-full\".");
108         }
109         index = val;
110     }
111
112     public final String JavaDoc getIndex() {
113         return index;
114     }
115
116
117     public final void setItems(int value) {
118         items = value;
119     }
120
121     public final int getItems() {
122         return items;
123     }
124
125
126     public final void setMaxItems(int value) {
127         maxItems = value;
128     }
129
130     public final int getMaxItems() {
131         return maxItems;
132     }
133
134
135     public final void setMaxPageItems(int value) {
136         maxPageItems = value;
137     }
138
139     public final int getMaxPageItems() {
140         return maxPageItems;
141     }
142
143
144     public final void setMaxIndexPages(int value) {
145         maxIndexPages = value;
146     }
147
148     public final int getMaxIndexPages() {
149         return maxIndexPages;
150     }
151
152
153     public final void setIsOffset(boolean val) {
154         isOffset = val;
155     }
156
157     public final boolean getIsOffset() {
158         return isOffset;
159     }
160
161
162     public final void setExport(String JavaDoc value) throws JspException {
163         if (export != value) {
164             try {
165                 pagerTagExport = TagExportParser.parsePagerTagExport(value);
166             } catch (ParseException ex) {
167                 throw new JspTagException(ex.getMessage());
168             }
169         }
170         export = value;
171     }
172
173     public final String JavaDoc getExport() {
174         return export;
175     }
176
177
178     public final void setScope(String JavaDoc val) throws JspException {
179         if (!(val == null || PAGE.equals(val) || REQUEST.equals(val)))
180         {
181             throw new JspTagException("value for attribute \"scope\" " +
182                 "must be either \"page\" or \"request\".");
183         }
184         scope = val;
185     }
186
187     public final String JavaDoc getScope() {
188         return scope;
189     }
190
191
192
193     final void addParam(String JavaDoc name, String JavaDoc value) {
194         if (value != null) {
195             name = java.net.URLEncoder.encode(name);
196             value = java.net.URLEncoder.encode(value);
197
198             uri.append(params == 0 ? '?' : '&')
199                .append(name).append('=').append(value);
200
201            params++;
202
203         } else {
204             String JavaDoc[] values = pageContext.getRequest().getParameterValues(name);
205
206             if (values != null) {
207                 name = java.net.URLEncoder.encode(name);
208                 for (int i = 0, l = values.length; i < l; i++) {
209                     value = java.net.URLEncoder.encode(values[i]);
210                     uri.append(params == 0 ? '?' : '&')
211                        .append(name).append('=').append(value);
212
213                     params++;
214                 }
215             }
216         }
217     }
218
219     final boolean nextItem() {
220         boolean showItem = false;
221         if (itemCount < maxItems) {
222             showItem = (itemCount >= offset &&
223                         itemCount < (offset + maxPageItems));
224             itemCount++;
225         }
226         return showItem;
227     }
228
229
230     final int getOffset() {
231         return offset;
232     }
233
234
235     final boolean isIndexNeeded() {
236         return (offset != 0 || getItemCount() > maxPageItems);
237     }
238
239
240     final boolean hasPrevPage() {
241         return (offset > 0);
242     }
243
244     final boolean hasNextPage() {
245         return (getItemCount() > getNextOffset());
246     }
247
248     final boolean hasPage(int page) {
249         return (page >= 0 && getItemCount() > (page * maxPageItems));
250     }
251
252
253     final int getPrevOffset() {
254         return Math.max(0, offset - maxPageItems);
255     }
256
257     final int getNextOffset() {
258         return offset + maxPageItems;
259     }
260
261
262     final String JavaDoc getOffsetUrl(int pageOffset) {
263         int uriLen = uri.length();
264         uri.append(params == 0 ? '?' : '&')
265            .append(idOffsetParam).append('=').append(pageOffset);
266         String JavaDoc offsetUrl = uri.toString();
267         uri.setLength(uriLen);
268         return offsetUrl;
269     }
270
271     final String JavaDoc getPageUrl(int i) {
272         return getOffsetUrl(maxPageItems * i);
273     }
274
275
276     final Integer JavaDoc getOffsetPageNumber(int pageOffset) {
277         return new Integer JavaDoc(1+pageNumber(pageOffset));
278     }
279
280     final Integer JavaDoc getPageNumber(int i) {
281         if (i == pageNumber)
282             return pageNumberInteger;
283         return new Integer JavaDoc(1+i);
284     }
285
286     final int getPageNumber() {
287         return pageNumber;
288     }
289
290     final int getPageCount() {
291         return pageNumber(getItemCount());
292     }
293
294
295     final int getFirstIndexPage() {
296         int firstPage = 0;
297         int halfIndexPages = maxIndexPages / 2;
298
299         if (FORWARD.equals(index)) {
300             firstPage = Math.min(pageNumber + 1, getPageCount());
301         } else if (!(HALF_FULL.equals(index) && pageNumber < halfIndexPages)) {
302             int pages = getPageCount();
303             if (pages > maxIndexPages) {
304                 // put the current page in middle of the index
305
firstPage = Math.max(0, pageNumber - halfIndexPages);
306
307                 int indexPages = pages - firstPage;
308                 if (indexPages < maxIndexPages)
309                     firstPage -= (maxIndexPages - indexPages);
310             }
311         }
312
313         return firstPage;
314     }
315
316     final int getLastIndexPage(int firstPage) {
317         int pages = getPageCount();
318         int halfIndexPages = maxIndexPages / 2;
319         int maxPages;
320         if (HALF_FULL.equals(index) && pageNumber < halfIndexPages) {
321             maxPages = pageNumber + halfIndexPages;
322         } else {
323             maxPages = firstPage + maxIndexPages;
324         }
325         return (pages <= maxPages ? pages : maxPages) - 1;
326     }
327
328
329     final int getItemCount() {
330         return (items != 0 ? items : itemCount);
331     }
332
333     private final int pageNumber(int offset) {
334         return (offset / maxPageItems) + (offset % maxPageItems == 0 ? 0 : 1);
335     }
336
337
338     public int doStartTag() throws JspException {
339
340         String JavaDoc baseUri;
341         if (url != null) {
342             baseUri = url;
343         } else {
344             baseUri = ((HttpServletRequest)pageContext.getRequest())
345                 .getRequestURI();
346             int i = baseUri.indexOf('?');
347             if (i != -1)
348                 baseUri = baseUri.substring(0, i);
349         }
350         if (uri == null)
351             uri = new StringBuffer JavaDoc(baseUri.length() + 32);
352         else
353             uri.setLength(0);
354         uri.append(baseUri);
355
356
357         params = 0;
358         offset = 0;
359         itemCount = 0;
360
361         String JavaDoc offsetParam =
362             pageContext.getRequest().getParameter(idOffsetParam);
363         if (offsetParam != null) {
364             try {
365                 offset = Math.max(0, Integer.parseInt(offsetParam));
366                 if (isOffset)
367                     itemCount = offset;
368             } catch (NumberFormatException JavaDoc ignore) {
369             }
370         }
371
372         pageNumber = pageNumber(offset);
373         pageNumberInteger = new Integer JavaDoc(1+pageNumber);
374
375
376         if (REQUEST.equals(scope)) {
377             ServletRequest request = pageContext.getRequest();
378
379             oldPager = request.getAttribute(id);
380             request.setAttribute(id, this);
381
382             if (pagerTagExport != null) {
383                 String JavaDoc name;
384                 if ((name = pagerTagExport.getPageOffset()) != null) {
385                     oldOffset = request.getAttribute(name);
386                     request.setAttribute(name, new Integer JavaDoc(offset));
387                 }
388                 if ((name = pagerTagExport.getPageNumber()) != null) {
389                     oldPageNumber = request.getAttribute(name);
390                     request.setAttribute(name, pageNumberInteger);
391                 }
392             }
393         } else {
394             if (pagerTagExport != null) {
395                 String JavaDoc name;
396                 if ((name = pagerTagExport.getPageOffset()) != null) {
397                     oldOffset = pageContext.getAttribute(name);
398                     pageContext.setAttribute(name, new Integer JavaDoc(offset));
399                 }
400                 if ((name = pagerTagExport.getPageNumber()) != null) {
401                     oldPageNumber = pageContext.getAttribute(name);
402                     pageContext.setAttribute(name, pageNumberInteger);
403                 }
404             }
405         }
406
407         return EVAL_BODY_INCLUDE;
408     }
409
410     private static void restoreAttribute(ServletRequest request, String JavaDoc name,
411         Object JavaDoc oldValue)
412     {
413         if (oldValue != null)
414             request.setAttribute(name, oldValue);
415         else
416             request.removeAttribute(name);
417     }
418
419     private static void restoreAttribute(PageContext pageContext, String JavaDoc name,
420         Object JavaDoc oldValue)
421     {
422         if (oldValue != null)
423             pageContext.setAttribute(name, oldValue);
424         else
425             pageContext.removeAttribute(name);
426     }
427
428
429     public int doEndTag() throws JspException {
430         if (REQUEST.equals(scope)) {
431             ServletRequest request = pageContext.getRequest();
432
433             restoreAttribute(request, id, oldPager);
434             oldPager = null;
435
436             if (pagerTagExport != null) {
437                 String JavaDoc name;
438                 if ((name = pagerTagExport.getPageOffset()) != null) {
439                     restoreAttribute(request, name, oldOffset);
440                     oldOffset = null;
441                 }
442
443                 if ((name = pagerTagExport.getPageNumber()) != null) {
444                     restoreAttribute(request, name, oldPageNumber);
445                     oldPageNumber = null;
446                 }
447             }
448         } else {
449             if (pagerTagExport != null) {
450                 String JavaDoc name;
451                 if ((name = pagerTagExport.getPageOffset()) != null) {
452                     restoreAttribute(pageContext, name, oldOffset);
453                     oldOffset = null;
454                 }
455
456                 if ((name = pagerTagExport.getPageNumber()) != null) {
457                     restoreAttribute(pageContext, name, oldPageNumber);
458                     oldPageNumber = null;
459                 }
460             }
461         }
462
463         // limit size of re-usable StringBuffer
464
if (uri.capacity() > 1024)
465             uri = null;
466
467         pageNumberInteger = null;
468
469         return EVAL_PAGE;
470     }
471
472     public void release() {
473         url = null;
474         index = null;
475         items = 0;
476         maxItems = DEFAULT_MAX_ITEMS;
477         maxPageItems = DEFAULT_MAX_PAGE_ITEMS;
478         maxIndexPages = DEFAULT_MAX_INDEX_PAGES;
479         isOffset = false;
480         export = null;
481         scope = null;
482
483         uri = null;
484         params = 0;
485         offset = 0;
486         itemCount = 0;
487         pageNumber = 0;
488         pageNumberInteger = null;
489
490         idOffsetParam = DEFAULT_ID+OFFSET_PARAM;
491         pagerTagExport = null;
492         oldPager = null;
493         oldOffset = null;
494         oldPageNumber = null;
495
496         super.release();
497     }
498 }
499
500 /* vim:set ts=4 sw=4: */
501
Popular Tags