ugo 2004/06/29 13:33:39
Modified: src/java/org/apache/cocoon/generation CalendarGenerator.java
Log:
Added support for padding initial and final weeks.
Submitted by: Colin Paul Adams
Revision Changes Path
1.10 +92 -12
cocoon-2.1/src/java/org/apache/cocoon/generation/CalendarGenerator.java
Index: CalendarGenerator.java
===================================================================
RCS file:
/home/cvs/cocoon-2.1/src/java/org/apache/cocoon/generation/CalendarGenerator.java,v
retrieving revision 1.9
retrieving revision 1.10
diff -u -r1.9 -r1.10
--- CalendarGenerator.java 26 May 2004 14:11:34 -0000 1.9
+++ CalendarGenerator.java 29 Jun 2004 20:33:38 -0000 1.10
@@ -39,6 +39,45 @@
/**
* @cocoon.sitemap.component.documentation
* Generates an XML document representing a calendar for a given month and
year.
+ * <p>
+ * Here is a sample output:
+ * <pre>
+ * <calendar:calendar
xmlns:calendar="http://apache.org/cocoon/calendar/1.0"
+ * year="2004" month="January" prevMonth="12" prevYear="2003"
+ * nextMonth="02" nextYear="2004">
+ * <calendar:week number="1">
+ * <calendar:day number="1" date="January 1, 2004"/>
+ * <calendar:day number="2" date="January 2, 2004"/>
+ * <calendar:day number="3" date="January 3, 2004"/>
+ * <calendar:day number="4" date="January 4, 2004"/>
+ * </calendar:week>
+ * ...
+ * </calendar:calendar>
+ * </pre>
+ * <p>
+ * The <i>src</i> parameter is ignored.
+ * </p>
+ * <p>
+ * <b>Configuration options:</b>
+ * <dl>
+ * <dt> <i>month</i> (optional)
+ * <dd> Sets the month for the calendar (January is 1). Default is the
current month.
+ * <dt> <i>year</i> (optional)
+ * <dd> Sets the year for the calendar. Default is the current year.
+ * <dt> <i>dateFormat</i> (optional)
+ * <dd> Sets the format for the date attribute of each node, as
+ * described in java.text.SimpleDateFormat. If unset, the default
+ * format for the current locale will be used.
+ * <dt> <i>lang</i> (optional)
+ * <dd> Sets the ISO language code for determining the locale.
+ * <dt> <i>country</i> (optional)
+ * <dd> Sets the ISO country code for determining the locale.
+ * <dt> <i>padWeeks</i> (optional)
+ * <dd> If set to true, full weeks will be generated by adding
+ * days from the end of the previous month and the beginning
+ * of the following month.
+ * </dl>
+ * </p>
*
* @cocoon.sitemap.component.name calendar
* @cocoon.sitemap.component.label content
@@ -95,6 +134,9 @@
/** The current locale */
protected Locale locale;
+ /** Do we need to pad out the first and last weeks? */
+ protected boolean padWeeks;
+
/**
* Set the request parameters. Must be called before the generate method.
*
@@ -109,7 +151,7 @@
this.cacheKeyParList = new ArrayList();
this.cacheKeyParList.add(src);
-
+
// Determine the locale
String langString = par.getParameter("lang", null);
locale = Locale.getDefault();
@@ -136,8 +178,9 @@
} else {
this.dateFormatter = DateFormat.getDateInstance(DateFormat.LONG,
locale);
}
+ this.padWeeks = par.getParameterAsBoolean("padWeeks", false);
+ this.cacheKeyParList.add(new Boolean(this.padWeeks));
this.monthFormatter = new SimpleDateFormat("MMMM", locale);
-
this.attributes = new AttributesImpl();
}
@@ -154,7 +197,7 @@
start.set(Calendar.DAY_OF_MONTH, 1);
Calendar end = (Calendar) start.clone();
end.add(Calendar.MONTH, 1);
-
+
// Determine previous and next months
Calendar prevMonth = (Calendar) start.clone();
prevMonth.add(Calendar.MONTH, -1);
@@ -175,18 +218,38 @@
String.valueOf(end.get(Calendar.YEAR)));
attributes.addAttribute("", NEXT_MONTH_ATTR_NAME,
NEXT_MONTH_ATTR_NAME, "CDATA",
monthNumberFormatter.format(end.get(Calendar.MONTH) + 1));
-
+
this.contentHandler.startElement(URI, CALENDAR_NODE_NAME,
PREFIX + ':' + CALENDAR_NODE_NAME, attributes);
int weekNo = start.get(Calendar.WEEK_OF_MONTH);
- if (start.get(Calendar.DAY_OF_WEEK) != start.getFirstDayOfWeek()) {
+ int firstDay = start.getFirstDayOfWeek();
+ if (start.get(Calendar.DAY_OF_WEEK) != firstDay) {
attributes.clear();
attributes.addAttribute("", NUMBER_ATTR_NAME, NUMBER_ATTR_NAME,
"CDATA", String.valueOf(weekNo));
this.contentHandler.startElement(URI, WEEK_NODE_NAME,
PREFIX + ':' + WEEK_NODE_NAME, attributes);
+ if (padWeeks) {
+ Calendar previous = (Calendar) start.clone();
+ while (previous.get(Calendar.DAY_OF_WEEK) != firstDay) {
+ previous.add(Calendar.DAY_OF_MONTH, -1);
+ }
+ while (previous.before(start)) {
+ attributes.clear();
+ attributes.addAttribute("", NUMBER_ATTR_NAME,
NUMBER_ATTR_NAME, "CDATA",
+
String.valueOf(previous.get(Calendar.DAY_OF_MONTH)));
+ attributes.addAttribute("", DATE_ATTR_NAME,
DATE_ATTR_NAME, "CDATA",
+ dateFormatter.format(previous.getTime()));
+ this.contentHandler.startElement(URI, DAY_NODE_NAME,
+ PREFIX + ':' + DAY_NODE_NAME, attributes);
+ addContent(previous, locale);
+ this.contentHandler.endElement(URI, DAY_NODE_NAME,
+ PREFIX + ':' + DAY_NODE_NAME);
+ previous.add(Calendar.DAY_OF_MONTH, 1);
+ }
+ }
}
while (start.before(end)) {
- if (start.get(Calendar.DAY_OF_WEEK) ==
start.getFirstDayOfWeek()) {
+ if (start.get(Calendar.DAY_OF_WEEK) == firstDay) {
weekNo = start.get(Calendar.WEEK_OF_MONTH);
attributes.clear();
attributes.addAttribute("", NUMBER_ATTR_NAME,
NUMBER_ATTR_NAME, "CDATA", String.valueOf(weekNo));
@@ -204,13 +267,30 @@
this.contentHandler.endElement(URI, DAY_NODE_NAME,
PREFIX + ':' + DAY_NODE_NAME);
start.add(Calendar.DAY_OF_MONTH, 1);
- if (start.get(Calendar.DAY_OF_WEEK) == start.getFirstDayOfWeek()
- || ! start.before(end)) {
+ if (start.get(Calendar.DAY_OF_WEEK) == firstDay
+ || (!padWeeks && ! start.before(end))) {
this.contentHandler.endElement(URI, WEEK_NODE_NAME,
PREFIX + ':' + WEEK_NODE_NAME);
}
}
+ if (padWeeks) {
+ while (firstDay != end.get(Calendar.DAY_OF_WEEK)) {
+ attributes.clear();
+ attributes.addAttribute("", NUMBER_ATTR_NAME,
NUMBER_ATTR_NAME, "CDATA",
+ String.valueOf(end.get(Calendar.DAY_OF_MONTH)));
+ attributes.addAttribute("", DATE_ATTR_NAME, DATE_ATTR_NAME,
"CDATA",
+ dateFormatter.format(end.getTime()));
+ this.contentHandler.startElement(URI, DAY_NODE_NAME,
+ PREFIX + ':' + DAY_NODE_NAME, attributes);
+ addContent(end, locale);
+ this.contentHandler.endElement(URI, DAY_NODE_NAME,
+ PREFIX + ':' + DAY_NODE_NAME);
+ end.add(Calendar.DAY_OF_MONTH, 1);
+ }
+ this.contentHandler.endElement(URI, WEEK_NODE_NAME,
+ PREFIX + ':' + WEEK_NODE_NAME);
+ }
this.contentHandler.endElement(URI, CALENDAR_NODE_NAME,
PREFIX + ':' + CALENDAR_NODE_NAME);
this.contentHandler.endPrefixMapping(PREFIX);
@@ -226,7 +306,7 @@
* @throws SAXException if an error occurs while outputting the document
*/
protected void addContent(Calendar date, Locale locale) throws
SAXException {}
-
+
/* (non-Javadoc)
* @see org.apache.cocoon.caching.CacheableProcessingComponent#getKey()
*/
@@ -234,7 +314,7 @@
StringBuffer buffer = new StringBuffer();
int len = this.cacheKeyParList.size();
for (int i = 0; i < len; i++) {
- buffer.append((String)this.cacheKeyParList.get(i) + ":");
+ buffer.append(this.cacheKeyParList.get(i) + ":");
}
return buffer.toString();
}
@@ -258,5 +338,5 @@
this.locale = null;
super.recycle();
}
-
+
}