001 /**
002 * Copyright 2004-2013 The Kuali Foundation
003 *
004 * Licensed under the Educational Community License, Version 2.0 (the "License");
005 * you may not use this file except in compliance with the License.
006 * You may obtain a copy of the License at
007 *
008 * http://www.opensource.org/licenses/ecl2.php
009 *
010 * Unless required by applicable law or agreed to in writing, software
011 * distributed under the License is distributed on an "AS IS" BASIS,
012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013 * See the License for the specific language governing permissions and
014 * limitations under the License.
015 */
016 package org.kuali.hr.time.calendar;
017
018 import org.joda.time.DateTime;
019 import org.kuali.hr.lm.leaveblock.LeaveBlock;
020 import org.kuali.hr.lm.util.LeaveBlockAggregate;
021 import org.kuali.hr.time.earncode.EarnCode;
022 import org.kuali.hr.time.service.base.TkServiceLocator;
023 import org.kuali.hr.time.timeblock.TimeBlock;
024 import org.kuali.hr.time.util.TkConstants;
025 import org.kuali.hr.time.util.TkTimeBlockAggregate;
026
027 import java.util.ArrayList;
028 import java.util.List;
029 import java.util.Map;
030
031 public class TkCalendar extends CalendarParent {
032 private CalendarEntries payCalEntry;
033 private DateTime beginDateTime;
034 private DateTime endDateTime;
035
036 public TkCalendar() {}
037
038 public TkCalendar(CalendarEntries calendarEntry) {
039 super(calendarEntry);
040 }
041
042 public static TkCalendar getCalendar(TkTimeBlockAggregate tbAggregate, LeaveBlockAggregate lbAggregate) {
043 TkCalendar tc = new TkCalendar();
044
045 if (tbAggregate != null && lbAggregate != null) {
046 if(tbAggregate.getDayTimeBlockList().size() != lbAggregate.getDayLeaveBlockList().size()){
047 throw new RuntimeException("TimeBlockAggregate and LeaveBlockAggregate should have the same size of Day Blocks List");
048 }
049
050 List<CalendarWeek> weeks = new ArrayList<CalendarWeek>();
051 tc.setPayCalEntry(tbAggregate.getPayCalendarEntry());
052
053 int firstDay = 0;
054 if (tc.getBeginDateTime().getDayOfWeek() != 7) {
055 firstDay = 0 - tc.getBeginDateTime().getDayOfWeek(); // always render calendar weeks from Sundays
056 }
057 for (int i = 0; i < tbAggregate.numberOfAggregatedWeeks(); i++) {
058 TkCalendarWeek week = new TkCalendarWeek();
059 List<List<TimeBlock>> weekBlocks = tbAggregate.getWeekTimeBlocks(i);
060 List<List<LeaveBlock>> weekLeaveBlocks = lbAggregate.getWeekLeaveBlocks(i);
061 List<CalendarDay> days = new ArrayList<CalendarDay>(7);
062
063 for (int j = 0; j < weekBlocks.size(); j++) {
064 List<TimeBlock> dayBlocks = weekBlocks.get(j);
065 List<LeaveBlock> dayLeaveBlocks = weekLeaveBlocks.get(j);
066 // Create the individual days.
067 TkCalendarDay day = new TkCalendarDay();
068 day.setTimeblocks(dayBlocks);
069 day.setLeaveBlocks(dayLeaveBlocks);
070 day.setDayNumberString(tc.getDayNumberString(i * 7 + j + firstDay));
071 day.setDayNumberDelta(i * 7 + j + firstDay);
072 day.setDateString(tc.getDateString(day.getDayNumberDelta()));
073 assignDayLunchLabel(day);
074 int dayIndex = i * 7 + j + firstDay;
075 DateTime beginDateTemp = tc.getBeginDateTime().plusDays(dayIndex);
076 day.setGray(false);
077 if (beginDateTemp.isBefore(tc.getBeginDateTime().getMillis())
078 || beginDateTemp.isAfter(tc.getEndDateTime().getMillis())) {
079 day.setGray(true);
080 }
081 if (tc.getEndDateTime().getHourOfDay() == 0 && beginDateTemp.equals(tc.getEndDateTime())) {
082 day.setGray(true);
083 }
084 days.add(day);
085 }
086 week.setDays(days);
087 weeks.add(week);
088 }
089 tc.setWeeks(weeks);
090 } else {
091 return null;
092 }
093
094 return tc;
095 }
096
097 public static TkCalendar getCalendar(TkTimeBlockAggregate aggregate) {
098 TkCalendar tc = new TkCalendar();
099
100 if (aggregate != null) {
101 List<CalendarWeek> weeks = new ArrayList<CalendarWeek>();
102 tc.setPayCalEntry(aggregate.getPayCalendarEntry());
103
104 int firstDay = 0;
105 if (tc.getBeginDateTime().getDayOfWeek() != 7) {
106 firstDay = 0 - tc.getBeginDateTime().getDayOfWeek(); // always render calendar weeks from Sundays
107 }
108 for (int i = 0; i < aggregate.numberOfAggregatedWeeks(); i++) {
109 TkCalendarWeek week = new TkCalendarWeek();
110 List<List<TimeBlock>> weekBlocks = aggregate.getWeekTimeBlocks(i);
111 List<CalendarDay> days = new ArrayList<CalendarDay>(7);
112
113 for (int j = 0; j < weekBlocks.size(); j++) {
114 List<TimeBlock> dayBlocks = weekBlocks.get(j);
115 // Create the individual days.
116 TkCalendarDay day = new TkCalendarDay();
117 day.setTimeblocks(dayBlocks);
118 day.setDayNumberString(tc.getDayNumberString(i * 7 + j + firstDay));
119 day.setDayNumberDelta(i * 7 + j + firstDay);
120 day.setDateString(tc.getDateString(day.getDayNumberDelta()));
121 assignDayLunchLabel(day);
122 int dayIndex = i * 7 + j + firstDay;
123 DateTime beginDateTemp = tc.getBeginDateTime().plusDays(dayIndex);
124 day.setGray(false);
125 if (beginDateTemp.isBefore(tc.getBeginDateTime().getMillis())
126 || beginDateTemp.isAfter(tc.getEndDateTime().getMillis())) {
127 day.setGray(true);
128 }
129 if (tc.getEndDateTime().getHourOfDay() == 0 && beginDateTemp.equals(tc.getEndDateTime())) {
130 day.setGray(true);
131 }
132 days.add(day);
133 }
134 week.setDays(days);
135 weeks.add(week);
136 }
137 tc.setWeeks(weeks);
138 } else {
139 return null;
140 }
141
142 return tc;
143 }
144
145 public static void assignDayLunchLabel(TkCalendarDay day) {
146 EarnCode ec = null;
147 String label = "";
148 String id = "";
149 for (TimeBlockRenderer tbr : day.getBlockRenderers()) {
150 for (TimeHourDetailRenderer thdr : tbr.getDetailRenderers()) {
151 if (thdr.getTitle().equals(TkConstants.LUNCH_EARN_CODE)) {
152 ec = TkServiceLocator.getEarnCodeService().getEarnCode(thdr.getTitle(), tbr.getTimeBlock().getBeginDate());
153 if (ec != null) {
154 label = ec.getDescription() + " : " + thdr.getHours() + " hours";
155 id = thdr.getTkTimeHourDetailId();
156 }
157 }
158 }
159 tbr.setLunchLabel(label);
160 tbr.setLunchLabelId(id);
161
162 label = "";
163 }
164 }
165
166
167 public void assignAssignmentStyle(Map<String, String> styleMap) {
168 for (CalendarWeek aWeek : this.getWeeks()) {
169 for (CalendarDay aDay : aWeek.getDays()) {
170 for (TimeBlockRenderer tbr : ((TkCalendarDay)aDay).getBlockRenderers()) {
171 String assignmentKey = tbr.getTimeBlock().getAssignmentKey();
172 if (assignmentKey != null && styleMap.containsKey(assignmentKey)) {
173 tbr.setAssignmentClass(styleMap.get(assignmentKey));
174 } else {
175 tbr.setAssignmentClass("");
176 }
177 }
178 for (LeaveBlockRenderer lbr : ((TkCalendarDay)aDay).getLeaveBlockRenderers()) {
179 String assignmentKey = lbr.getLeaveBlock().getAssignmentKey();
180 if (assignmentKey != null && styleMap.containsKey(assignmentKey)) {
181 lbr.setAssignmentClass(styleMap.get(assignmentKey));
182 } else {
183 lbr.setAssignmentClass("");
184 }
185 }
186
187 }
188 }
189 }
190
191 public CalendarEntries getPayCalEntry() {
192 return payCalEntry;
193 }
194
195 public void setPayCalEntry(CalendarEntries payCalEntry) {
196 this.payCalEntry = payCalEntry;
197 // Relative time, with time zone added.
198 this.beginDateTime = payCalEntry.getBeginLocalDateTime().toDateTime(TkServiceLocator.getTimezoneService().getUserTimezoneWithFallback());
199 this.endDateTime = payCalEntry.getEndLocalDateTime().toDateTime(TkServiceLocator.getTimezoneService().getUserTimezoneWithFallback());
200 }
201
202 public DateTime getBeginDateTime() {
203 return beginDateTime;
204 }
205
206 public DateTime getEndDateTime() {
207 return endDateTime;
208 }
209
210 /**
211 * Provides the calendar title / heading. If the Pay Calendar entry spans
212 * multiple months, you get Abbreviated Month name + year of both the
213 * beginning month and the ending month.
214 *
215 * @return String for calendar title use.
216 */
217 public String getCalendarTitle() {
218 StringBuilder sb = new StringBuilder();
219
220 if (getBeginDateTime().getMonthOfYear() == getEndDateTime().getMonthOfYear() ||
221 (getBeginDateTime().getMonthOfYear() != getEndDateTime().getMonthOfYear()
222 && getEndDateTime().getDayOfMonth() == 1 && getEndDateTime().getSecondOfDay() == 0)) {
223 sb.append(getBeginDateTime().toString("MMMM y"));
224 } else {
225 sb.append(getBeginDateTime().toString("MMM y"));
226 sb.append(" - ");
227 sb.append(getEndDateTime().toString("MMM y"));
228 }
229
230 return sb.toString();
231 }
232
233 /**
234 * Assumption of 7 "days" per week, or 7 "blocks" per row.
235 *
236 * @return A list of string titles for each row block (day)
237 */
238 public List<String> getCalendarDayHeadings() {
239 List<String> dayStrings = new ArrayList<String>(7);
240 // always render from Sunday
241 int firstDay = 0 - getBeginDateTime().getDayOfWeek();
242 int lastDay = firstDay + 7;
243
244 if (getBeginDateTime().getMinuteOfDay() == 0) {
245 // "Standard" days.
246 for (int i = firstDay; i < lastDay; i++) {
247 DateTime currDay = getBeginDateTime().plusDays(i);
248 dayStrings.add(currDay.toString("E"));
249 }
250 } else {
251 // Day Split Strings
252
253 for (int i = firstDay; i < lastDay; i++) {
254 StringBuilder builder = new StringBuilder("");
255 DateTime currStart = getBeginDateTime().plusDays(i);
256 DateTime currEnd = getBeginDateTime().plusDays(i);
257
258 builder.append(currStart.toString("E HH:mm"));
259 builder.append(" - ");
260 builder.append(currEnd.toString("E HH:mm"));
261
262 dayStrings.add(builder.toString());
263 }
264 }
265
266 return dayStrings;
267 }
268
269 public String getCalenadrYear() {
270 return getBeginDateTime().toString("yyyy");
271 }
272
273 public String getCalendarMonth() {
274 return getBeginDateTime().toString("M");
275 }
276
277 private String getDayNumberString(int dayDelta) {
278 StringBuilder b = new StringBuilder();
279
280 if (getBeginDateTime().getMinuteOfDay() == 0) {
281 DateTime currStart = getBeginDateTime().plusDays(dayDelta);
282 b.append(currStart.toString("d"));
283 } else {
284 DateTime currStart = getBeginDateTime().plusDays(dayDelta);
285 DateTime currEnd = getBeginDateTime().plusDays(dayDelta);
286
287 b.append(currStart.toString("d HH:mm"));
288 b.append(" - ");
289 //TODO: should this be currEnd???
290 b.append(currStart.toString("d HH:mm"));
291 }
292
293 return b.toString();
294 }
295
296 private String getDateString(int dayDelta) {
297 return getBeginDateTime().plusDays(dayDelta).toString("M/d/yyyy");
298 }
299
300 }