View Javadoc

1   /***
2    * Copyright (C) 2005 The Java Community
3    *
4    * This program is free software; you can redistribute it and/or modify it under
5    * the terms of the GNU General Public License as published by the Free Software
6    * Foundation; either version 2 of the License, or (at your option) any later
7    * version.
8    *
9    * This program is distributed in the hope that it will be useful, but WITHOUT
10   * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
11   * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more
12   * details.
13   *
14   * You should have received a copy of the GNU General Public License along with
15   * this program; if not, write to the Free Software Foundation, Inc., 59 Temple
16   * Place, Suite 330, Boston, MA 02111-1307 USA.
17   *
18   */
19  
20  package org.bejug.javacareers.common.view.jsf.pager;
21  
22  import java.io.IOException;
23  import java.util.Iterator;
24  import java.util.Map;
25  
26  import javax.faces.component.NamingContainer;
27  import javax.faces.component.UIComponent;
28  import javax.faces.component.UIData;
29  import javax.faces.component.UIForm;
30  import javax.faces.context.FacesContext;
31  import javax.faces.context.ResponseWriter;
32  import javax.faces.el.ValueBinding;
33  import javax.faces.render.Renderer;
34  
35  /***
36   *
37   * @author ???? (last modified by $Author: shally $)
38   * @version $Revision: 1.15 $ - $Date: 2005/12/20 15:36:46 $
39   */
40  public class PagerRenderer extends Renderer {
41  
42      /***
43       * The logger.
44       */
45    //  private static final Log LOG = LogFactory.getLog(PagerRenderer.class);
46  
47     /***
48      * @param context FacesContext
49      * @param component UIComponent
50      * @throws IOException
51      * Overrides the parent's encodeBegin method.
52      */
53     public void encodeBegin(FacesContext context, UIComponent component)
54        throws IOException {
55        String id = component.getClientId(context);
56        UIComponent parent = component;
57        while (!(parent instanceof UIForm)) {
58            parent = parent.getParent();
59        }
60        String formId = parent.getClientId(context);
61  
62        ResponseWriter writer = context.getResponseWriter();
63  
64        String styleClass = (String) get(context, component, "styleClass");
65        String dataTableId = (String) get(context, component, "dataTableId");
66        // find the component with the given ID
67  
68        UIData data = (UIData) findComponent(context.getViewRoot(),
69           getId(dataTableId, id), context);
70        int first = data.getFirst();
71        int itemcount = data.getRowCount();
72        int pagesize = data.getRows();
73        if (pagesize <= 0) {
74            pagesize = itemcount;
75        }
76        int pages = itemcount / pagesize;
77        if (itemcount % pagesize != 0) {
78            pages++;
79        }
80        
81        if (pages > 1) {
82      	  int currentPage = first / pagesize;
83  
84      	  if (first >= itemcount - pagesize) {
85      		  currentPage = pages - 1;
86      	  }
87  	
88  	      if (currentPage > 0) {
89  	         writeLink(writer, component, formId, id, "Newer", styleClass);
90  	      }
91  
92            int last = pagesize + first > itemcount ? itemcount : pagesize + first;
93  	      writer.write("&nbsp;" + Integer.toString(first + 1) + " - " + Integer.toString(last) + " of " + Integer.toString(itemcount) + "&nbsp;");
94  
95  	      if (first < itemcount - pagesize) {
96  	         writeLink(writer, component, formId, id, "Older", styleClass);
97  	      }
98        }
99        // hidden field to hold result
100       writeHiddenField(writer, component, id);
101    }
102 
103    /***
104     *
105     * @param writer ResponseWriter
106     * @param component UIComponent
107     * @param formId String
108     * @param id String
109     * @param value String
110     * @param styleClass String
111     * @throws IOException e
112     */
113    private void writeLink(ResponseWriter writer, UIComponent component,
114       String formId, String id, String value, String styleClass)
115       throws IOException {
116       writer.writeText(" ", null);
117       writer.startElement("a", component);
118       writer.writeAttribute("href", "#", null);
119       writer.writeAttribute("onclick", onclickCode(formId, id, value), null);
120       if (styleClass != null) {
121          writer.writeAttribute("class", styleClass, "styleClass");
122       }
123       writer.writeText(value, null);
124       writer.endElement("a");
125    }
126 
127    /***
128     *
129     * @param formId String
130     * @param id String
131     * @param value String
132     * @return the code
133     */
134 
135    private String onclickCode(String formId, String id, String value) {
136       StringBuffer buffer = new StringBuffer();
137       buffer.append("document.forms[");
138       buffer.append("'");
139       buffer.append(formId);
140       buffer.append("'");
141       buffer.append("]['");
142       buffer.append(id);
143       buffer.append("'].value='");
144       buffer.append(value);
145       buffer.append("';");
146       buffer.append(" document.forms[");
147       buffer.append("'");
148       buffer.append(formId);
149       buffer.append("'");
150       buffer.append("].submit()");
151       buffer.append("; return false;");
152       return buffer.toString();
153    }
154 
155    /***
156     *
157     * @param writer ResponseWriter
158     * @param component UIComponent
159     * @param id String
160     * @throws IOException e
161     */
162    private void writeHiddenField(ResponseWriter writer, UIComponent component,
163       String id) throws IOException {
164       writer.startElement("input", component);
165       writer.writeAttribute("type", "hidden", null);
166       writer.writeAttribute("name", id, null);
167       writer.endElement("input");
168    }
169 
170    /*
171     * (non-Javadoc)
172     * @see javax.faces.render.Renderer#decode(javax.faces.context.FacesContext, javax.faces.component.UIComponent)
173     */
174    /***
175     * @param context FacesContext
176     * @param component UIComponent
177     * Overrides the parent's decode method
178     */
179    public void decode(FacesContext context, UIComponent component) {
180       //LOG.info("Debug: decode method called");
181       String id = component.getClientId(context);
182       Map parameters = context.getExternalContext()
183          .getRequestParameterMap();
184 
185       String response = (String) parameters.get(id);
186       //LOG.info("Debug: response = " + response);
187       //on call of table sorter method, this parameter is not set on the request.
188       //--> set the page to "1" by default
189       if (response.equals("")) {
190           response = "1";
191       }
192       String dataTableId = (String) get(context, component, "dataTableId");
193       UIData data = (UIData) findComponent(context.getViewRoot(),
194          getId(dataTableId, id), context);
195 
196       int first = data.getFirst();
197       int itemcount = data.getRowCount();
198       int pagesize = data.getRows();
199       if (pagesize <= 0) {
200           pagesize = itemcount;
201       }
202       
203       if (response.equals("Newer")) {
204           first -= pagesize;
205       } else if (response.equals("Older")) {
206           first += pagesize;
207      }
208       else{
209          int page = Integer.parseInt(response);
210          first = (page - 1) * pagesize;
211       }
212 
213       if (first < 0) {
214           first = 0;
215       }
216       data.setFirst(first);
217 
218    }
219 
220    /***
221     *
222     * @param context FacesContext
223     * @param component UIComponent
224     * @param name String
225     * @return the object
226     */
227    private static Object get(FacesContext context, UIComponent component,
228       String name) {
229       ValueBinding binding = component.getValueBinding(name);
230       if (binding != null) {
231           return binding.getValue(context);
232       }
233 	  return component.getAttributes().get(name);
234    }
235 
236    /***
237     *
238     * @param component UIComponent
239     * @param id String
240     * @param context FacesContext
241     * @return the component
242     */
243    private static UIComponent findComponent(UIComponent component, String id,
244            FacesContext context) {
245            String componentId = component.getClientId(context);
246            if (componentId.equals(id)) {
247                // LOG.info("Debug: componentId.equals(id), component = " + component.getClass().getName()
248                // + " id = " + component.getId());
249            	return component;
250            }
251            Iterator kids = component.getChildren().iterator();
252            while (kids.hasNext()) {
253               UIComponent kid = (UIComponent) kids.next();
254               UIComponent found = findComponent(kid, id, context);
255               if (found != null) {
256               	//LOG.info("Debug: found = " + found.getFamily());
257               	return found;
258               }
259            }
260            return null;
261         }
262 
263    /***
264     *
265     * @param id String
266     * @param baseId String
267     * @return the Id
268     */
269    private static String getId(String id, String baseId) {
270       String separator = "" + NamingContainer.SEPARATOR_CHAR;
271       String[] idSplit = id.split(separator);
272       String[] baseIdSplit = baseId.split(separator);
273       StringBuffer buffer = new StringBuffer();
274       for (int i = 0; i < baseIdSplit.length - idSplit.length; i++) {
275          buffer.append(baseIdSplit[i]);
276          buffer.append(separator);
277       }
278       buffer.append(id);
279       return buffer.toString();
280    }
281 }
282 
283 /***
284  * $Log: PagerRenderer.java,v $
285  * Revision 1.15  2005/12/20 15:36:46  shally
286  * CheckStyle and PMD changes.
287  *
288  * Revision 1.14  2005/09/30 14:38:07  bavo_jcs
289  * Fixed URL
290  *
291  * Revision 1.13  2005/09/13 08:11:06  schauwvliege
292  * organize imports
293  *
294  * Revision 1.12  2005/08/23 10:18:47  bme_jcs
295  * resolved checkstyle and pmd errors
296  *
297  * Revision 1.11  2005/08/22 15:29:04  psong09
298  * modified pager to JAVACAREERS-289 requirement
299  *
300  * Revision 1.10  2005/08/17 11:57:36  bme_jcs
301  * fixed little paging-bug
302  *
303  * Revision 1.9  2005/08/17 09:26:36  bme_jcs
304  * last page showed 10 jobs, now only what's left to avoid confusion
305  *
306  * Revision 1.8  2005/08/17 09:09:18  bme_jcs
307  * fixed a little bug in the paging
308  *
309  * Revision 1.7  2005/08/10 09:04:46  bavo_jcs
310  * Optimized imports according to checkstyle
311  *
312  * Revision 1.6  2005/08/09 12:59:54  bavo_jcs
313  * Optimized imports
314  *
315  * Revision 1.5  2005/06/21 15:19:59  psong09
316  * added custom component 'comment'
317  *
318  * Revision 1.4  2005/06/17 11:42:47  schauwvliege
319  * CheckStyle/ PMD
320  *
321  * Revision 1.3  2005/06/14 12:05:55  schauwvliege
322  * CheckStyle and fixing tests
323  *
324  * Revision 1.2  2005/06/09 08:18:41  bejug_cc
325  * Fix initial import
326  *
327  * Revision 1.9  2005/06/02 19:37:08  sja
328  * fix on 1 page display.
329  *
330  * Revision 1.8  2005/06/01 20:35:17  sja
331  * If we've only 1 page, then pager is not activated.
332  *
333  * Revision 1.7  2005/05/19 13:55:24  PSONG09
334  * update resume component + refactoring cv to resume
335  *
336  * Revision 1.6  2005/05/19 09:04:48  PSONG09
337  * modified jobsearch result table + CSS
338  *
339  * Revision 1.5  2005/05/18 15:13:29  PSONG09
340  * readded logger
341  *
342  * Revision 1.4  2005/05/11 12:49:30  ssc
343  * Checstyle errors
344  *
345  * Revision 1.3  2005/05/09 08:57:15  ssc
346  * Checkstyle
347  *
348  * Revision 1.2  2005/05/03 14:51:48  PSONG09
349  * update sorter and pager, javadoc added
350  *
351  * Revision 1.1  2005/05/02 15:44:00  PSONG09
352  * moved pager to common package
353  *
354  * Revision 1.2  2005/04/29 18:17:34  sja
355  * General cleanup (naming conv., javadoc and CVS tags)
356  *
357  */