1 16 17 package javax.servlet.jsp.jstl.core; 18 19 import javax.servlet.jsp.JspException ; 20 import javax.servlet.jsp.JspTagException ; 21 import javax.servlet.jsp.PageContext ; 22 import javax.servlet.jsp.tagext.IterationTag ; 23 import javax.servlet.jsp.tagext.TagSupport ; 24 import javax.servlet.jsp.tagext.TryCatchFinally ; 25 26 63 64 public abstract class LoopTagSupport 65 extends TagSupport 66 implements LoopTag, IterationTag , TryCatchFinally 67 { 68 71 80 81 82 protected int begin; 83 84 90 protected int end; 91 92 93 protected int step; 94 95 96 protected boolean beginSpecified; 97 98 99 protected boolean endSpecified; 100 101 102 protected boolean stepSpecified; 103 104 105 protected String itemId, statusId; 106 107 108 111 129 private LoopTagStatus status; private Object item; private int index; private int count; private boolean last; 135 138 144 public LoopTagSupport() { 145 super(); 146 init(); 147 } 148 149 150 153 172 protected abstract Object next() throws JspTagException ; 173 174 188 protected abstract boolean hasNext() throws JspTagException ; 189 190 198 protected abstract void prepare() throws JspTagException ; 199 200 201 204 207 public void release() { 208 super.release(); 209 init(); 210 } 211 212 215 public int doStartTag() throws JspException { 216 if (end != -1 && begin > end) { 217 return SKIP_BODY; 219 } 220 221 index = 0; 223 count = 1; 224 last = false; 225 226 prepare(); 228 229 discardIgnoreSubset(begin); 231 232 if (hasNext()) 234 item = next(); 236 else 237 return SKIP_BODY; 238 239 243 discard(step - 1); 244 245 exposeVariables(); 247 calibrateLast(); 248 return EVAL_BODY_INCLUDE; 249 } 250 251 255 public int doAfterBody() throws JspException { 256 257 index += step - 1; 259 260 count++; 262 263 if (hasNext() && !atEnd()) { 265 index++; 266 item = next(); 267 } else 268 return SKIP_BODY; 269 270 274 discard(step - 1); 275 276 exposeVariables(); 278 calibrateLast(); 279 return EVAL_BODY_AGAIN; 280 } 281 282 289 public void doFinally() { 290 294 unExposeVariables(); 295 } 296 297 300 public void doCatch(Throwable t) throws Throwable { 301 throw t; 302 } 303 304 307 314 315 320 public Object getCurrent() { 321 return item; 322 } 323 324 331 public LoopTagStatus getLoopStatus() { 332 333 class Status implements LoopTagStatus { 335 336 341 342 public Object getCurrent() { 343 349 return (LoopTagSupport.this.getCurrent()); 350 } 351 public int getIndex() { 352 return (index + begin); } 354 public int getCount() { 355 return (count); 356 } 357 public boolean isFirst() { 358 return (index == 0); } 360 public boolean isLast() { 361 return (last); } 363 public Integer getBegin() { 364 if (beginSpecified) 365 return (new Integer (begin)); 366 else 367 return null; 368 } 369 public Integer getEnd() { 370 if (endSpecified) 371 return (new Integer (end)); 372 else 373 return null; 374 } 375 public Integer getStep() { 376 if (stepSpecified) 377 return (new Integer (step)); 378 else 379 return null; 380 } 381 } 382 383 388 if (status == null) 389 status = new Status(); 390 391 return status; 392 } 393 394 404 405 411 public void setVar(String id) { 412 this.itemId = id; 413 } 414 415 421 public void setVarStatus(String statusId) { 422 this.statusId = statusId; 423 } 424 425 426 429 434 435 439 protected void validateBegin() throws JspTagException { 440 if (begin < 0) 441 throw new JspTagException ("'begin' < 0"); 442 } 443 444 448 protected void validateEnd() throws JspTagException { 449 if (end < 0) 450 throw new JspTagException ("'end' < 0"); 451 } 452 453 457 protected void validateStep() throws JspTagException { 458 if (step < 1) 459 throw new JspTagException ("'step' <= 0"); 460 } 461 462 463 466 467 private void init() { 468 index = 0; count = 1; status = null; item = null; last = false; beginSpecified = false; endSpecified = false; stepSpecified = false; 478 begin = 0; end = -1; step = 1; itemId = null; statusId = null; } 485 486 487 private void calibrateLast() throws JspTagException { 488 492 last = !hasNext() || atEnd() || 493 (end != -1 && (begin + index + step > end)); 494 } 495 496 501 private void exposeVariables() throws JspTagException { 502 503 519 520 if (itemId != null) { 521 if (getCurrent() == null) 522 pageContext.removeAttribute(itemId, PageContext.PAGE_SCOPE); 523 else 524 pageContext.setAttribute(itemId, getCurrent()); 525 } 526 if (statusId != null) { 527 if (getLoopStatus() == null) 528 pageContext.removeAttribute(statusId, PageContext.PAGE_SCOPE); 529 else 530 pageContext.setAttribute(statusId, getLoopStatus()); 531 } 532 533 } 534 535 539 private void unExposeVariables() { 540 if (itemId != null) 542 pageContext.removeAttribute(itemId, PageContext.PAGE_SCOPE); 543 if (statusId != null) 544 pageContext.removeAttribute(statusId, PageContext.PAGE_SCOPE); 545 } 546 547 560 private void discard(int n) throws JspTagException { 561 565 int oldIndex = index; 566 while (n-- > 0 && !atEnd() && hasNext()) { 567 index++; 568 next(); 569 } 570 index = oldIndex; 571 } 572 573 578 private void discardIgnoreSubset(int n) throws JspTagException { 579 while (n-- > 0 && hasNext()) 580 next(); 581 } 582 583 589 private boolean atEnd() { 590 return ((end != -1) && (begin + index >= end)); 591 } 592 } 593 | Popular Tags |