From cceeebc234a703f6fb37c0d50c7ca89d1c2a2325 Mon Sep 17 00:00:00 2001 From: Wolfgang Sourdeau Date: Thu, 11 Feb 2010 02:36:43 +0000 Subject: [PATCH] Monotone-Parent: 14183e9d9367b240b6e0585031a87772c952285a Monotone-Revision: 6550d093f75808cf03c8781a80f346a0cedf836a Monotone-Author: wsourdeau@inverse.ca Monotone-Date: 2010-02-11T02:36:43 Monotone-Branch: ca.inverse.sogo --- ChangeLog | 45 + UI/Scheduler/GNUmakefile | 1 + .../Toolbars/SOGoAppointmentFolders.toolbar | 4 +- UI/Scheduler/UIxAppointmentActions.h | 32 + UI/Scheduler/UIxAppointmentActions.m | 97 ++ UI/Scheduler/UIxAppointmentEditor.m | 17 +- UI/Scheduler/UIxCalDayTable.m | 4 +- UI/Scheduler/UIxCalListingActions.m | 11 +- UI/Scheduler/UIxOccurenceDialog.m | 7 + UI/Scheduler/product.plist | 17 +- UI/Templates/SchedulerUI/UIxCalDayTable.wox | 2 +- UI/Templates/SchedulerUI/UIxCalMainView.wox | 1 + UI/WebServerResources/HTMLElement.js | 2 +- UI/WebServerResources/SchedulerUI.css | 141 ++- UI/WebServerResources/SchedulerUI.js | 328 ++++-- UI/WebServerResources/SchedulerUIDnD.js | 933 ++++++++++++++++++ UI/WebServerResources/UIxOccurenceDialog.js | 7 + UI/WebServerResources/event-grippy-bottom.png | Bin 0 -> 179 bytes UI/WebServerResources/event-grippy-top.png | Bin 0 -> 178 bytes UI/WebServerResources/generic.css | 4 +- UI/WebServerResources/generic.js | 74 +- 21 files changed, 1530 insertions(+), 197 deletions(-) create mode 100644 UI/Scheduler/UIxAppointmentActions.h create mode 100644 UI/Scheduler/UIxAppointmentActions.m create mode 100644 UI/WebServerResources/SchedulerUIDnD.js create mode 100644 UI/WebServerResources/event-grippy-bottom.png create mode 100644 UI/WebServerResources/event-grippy-top.png diff --git a/ChangeLog b/ChangeLog index 256421b53..dbec6e291 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,48 @@ +2010-02-10 Wolfgang Sourdeau + + * UI/WebServerResources/SchedulerUI.js (newEvent): removed the + useless "sender" parameter and added "day", "hour" and "duration" + parameters to obtain a more generic method. + (newEventFromWidget): new method the previous "newEvent" incarnation. + (minutesToHM): new method that converts an amount of minutes into + a string value suitable for an "hm" query parameter. + (newEventFromDragging): new method suitable as a drag and drop + callback for creating events. + (updateEventFromDragging): new method suitable as a drag and drop + callback for adjusting events. + (_setupEventsDragAndDrop): new method that setups drag and drop + controllers for instances of events per calendar. + (attachDragControllers): new method that instantiate a drag and + drop controller for each day column. + + * UI/Scheduler/UIxCalListingActions.m + (_fillBlocks:withEvent:withNumber:): work around the situation + where the event start would occur after its end, causing a crash. + Still emits a warning. + + * UI/Scheduler/UIxCalDayTable.m (-currentHourLineId): new method + replacing "currentHourLineClass". The hour identifier now being + the value of the element id, the hourline classes are populated + from the template itself. + + * UI/WebServerResources/generic.js (generateQueryString): adjusted + method to take only "string" and "number" typed values into + account when constructing URL parameters. + + * UI/WebServerResources/SchedulerUIDnD.js: new js module with + classes implementing drag and drop of events. + + * UI/Scheduler/UIxOccurenceDialog.m (-confirmAdjustmentMethod): + new method for displaying a dialog suitable for start and duration + adjustments. + + * UI/Scheduler/UIxAppointmentActions.m (-adjustAction): new method + that takes a "days", a "start" and a "duration" relative + parameters to adjust the current event or occurrence. + + * UI/Scheduler/UIxAppointmentActions.[hm]: new module implementing + a WODirectAction class for ajax calls for appointments. + 2010-02-03 Wolfgang Sourdeau * UI/MainUI/SOGoRootPage.m (-_standardDefaultAction): add an diff --git a/UI/Scheduler/GNUmakefile b/UI/Scheduler/GNUmakefile index 640e4da96..ed4e002d4 100644 --- a/UI/Scheduler/GNUmakefile +++ b/UI/Scheduler/GNUmakefile @@ -36,6 +36,7 @@ SchedulerUI_OBJC_FILES = \ UIxAttendeesEditor.m \ UIxComponentEditor.m \ UIxCalendarSelector.m \ + UIxAppointmentActions.m \ UIxAppointmentEditor.m \ UIxTaskEditor.m \ UIxDatePicker.m \ diff --git a/UI/Scheduler/Toolbars/SOGoAppointmentFolders.toolbar b/UI/Scheduler/Toolbars/SOGoAppointmentFolders.toolbar index 65618f42a..4e09a1ffc 100644 --- a/UI/Scheduler/Toolbars/SOGoAppointmentFolders.toolbar +++ b/UI/Scheduler/Toolbars/SOGoAppointmentFolders.toolbar @@ -2,13 +2,13 @@ ( { link = "#"; isSafe = NO; label = "New Event"; - onclick = "return newEvent(this, 'event');"; + onclick = "return newEvent('event');"; image = "new-event.png"; tooltip = "Create a new event"; }, { link = "new_task"; label="New Task"; image = "new-task.png"; - onclick = "return newEvent(this, 'task');"; + onclick = "return newEvent('task');"; image = "new-task.png"; tooltip = "Create a new task"; } ), ( { link = "today"; diff --git a/UI/Scheduler/UIxAppointmentActions.h b/UI/Scheduler/UIxAppointmentActions.h new file mode 100644 index 000000000..58657e3d1 --- /dev/null +++ b/UI/Scheduler/UIxAppointmentActions.h @@ -0,0 +1,32 @@ +/* UIxAppointmentActions.h - this file is part of SOGo + * + * Copyright (C) 2010 Inverse inc. + * + * Author: Wolfgang Sourdeau + * + * This file is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2, or (at your option) + * any later version. + * + * This file is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; see the file COPYING. If not, write to + * the Free Software Foundation, Inc., 59 Temple Place - Suite 330, + * Boston, MA 02111-1307, USA. + */ + +#ifndef UIXAPPOINTMENTACTIONS_H +#define UIXAPPOINTMENTACTIONS_H + +#import + +@interface UIxAppointmentActions : WODirectAction + +@end + +#endif /* UIXAPPOINTMENTACTIONS_H */ diff --git a/UI/Scheduler/UIxAppointmentActions.m b/UI/Scheduler/UIxAppointmentActions.m new file mode 100644 index 000000000..70f857274 --- /dev/null +++ b/UI/Scheduler/UIxAppointmentActions.m @@ -0,0 +1,97 @@ +/* UIxAppointmentActions.m - this file is part of SOGo + * + * Copyright (C) 2010 Inverse inc. + * + * Author: Wolfgang Sourdeau + * + * This file is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2, or (at your option) + * any later version. + * + * This file is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; see the file COPYING. If not, write to + * the Free Software Foundation, Inc., 59 Temple Place - Suite 330, + * Boston, MA 02111-1307, USA. + */ + +#import +#import + +#import +#import +#import + +#import + +#import +#import +#import +#import + +#import + +#import "UIxAppointmentActions.h" + +@implementation UIxAppointmentActions + +- (WOResponse *) adjustAction +{ + WOResponse *response; + WORequest *rq; + SOGoAppointmentObject *co; + iCalEvent *event; + NSCalendarDate *start, *newStart, *end, *newEnd; + NSTimeInterval newDuration; + SOGoUserDefaults *ud; + NSString *daysDelta, *startDelta, *durationDelta; + NSTimeZone *tz; + + rq = [context request]; + + daysDelta = [rq formValueForKey: @"days"]; + startDelta = [rq formValueForKey: @"start"]; + durationDelta = [rq formValueForKey: @"duration"]; + if ([daysDelta length] > 0 + || [startDelta length] > 0 || [durationDelta length] > 0) + { + co = [self clientObject]; + event = (iCalEvent *) [[self clientObject] occurence]; + + ud = [[context activeUser] userDefaults]; + tz = [ud timeZone]; + start = [event startDate]; + [start setTimeZone: tz]; + + newStart = [start dateByAddingYears: 0 months: 0 + days: [daysDelta intValue] + hours: 0 minutes: [startDelta intValue] + seconds: 0]; + end = [event endDate]; + [end setTimeZone: tz]; + + newDuration = ([end timeIntervalSinceDate: start] + + [durationDelta intValue] * 60); + newEnd = [newStart addTimeInterval: newDuration]; + + [event setStartDate: newStart]; + [event setEndDate: newEnd]; + [co saveComponent: event]; + + response = [self responseWith204]; + } + else + response + = (WOResponse *) [NSException exceptionWithHTTPStatus: 400 + reason: @"missing 'days', 'start' and/or 'duration' parameters"]; + + + return response; +} + +@end diff --git a/UI/Scheduler/UIxAppointmentEditor.m b/UI/Scheduler/UIxAppointmentEditor.m index a768fd448..3a87a5b63 100644 --- a/UI/Scheduler/UIxAppointmentEditor.m +++ b/UI/Scheduler/UIxAppointmentEditor.m @@ -244,7 +244,7 @@ NSCalendarDate *startDate, *endDate; NSString *duration; NSTimeZone *timeZone; - unsigned int minutes; + unsigned int total, hours, minutes; SOGoObject *co; SOGoUserDefaults *ud; @@ -258,14 +258,21 @@ && [co isKindOfClass: [SOGoCalendarComponent class]]) { startDate = [self newStartDate]; - duration = [self queryParameterForKey:@"dur"]; + duration = [self queryParameterForKey:@"duration"]; if ([duration length] > 0) - minutes = [duration intValue]; + { + total = [duration intValue]; + hours = total / 100; + minutes = total % 100; + } else - minutes = 60; + { + hours = 1; + minutes = 0; + } endDate = [startDate dateByAddingYears: 0 months: 0 days: 0 - hours: 0 minutes: minutes seconds: 0]; + hours: hours minutes: minutes seconds: 0]; } else { diff --git a/UI/Scheduler/UIxCalDayTable.m b/UI/Scheduler/UIxCalDayTable.m index a38c44860..85b06ae67 100644 --- a/UI/Scheduler/UIxCalDayTable.m +++ b/UI/Scheduler/UIxCalDayTable.m @@ -143,9 +143,9 @@ return hoursToDisplay; } -- (NSString *) currentHourLineClass +- (NSString *) currentHourLineId { - return [NSString stringWithFormat: @"hourLine hourLine%d", [currentTableHour intValue]]; + return [NSString stringWithFormat: @"hourLine%d", [currentTableHour intValue]]; } - (NSArray *) daysToDisplay diff --git a/UI/Scheduler/UIxCalListingActions.m b/UI/Scheduler/UIxCalListingActions.m index c3d36d1f3..bd2de42f7 100644 --- a/UI/Scheduler/UIxCalListingActions.m +++ b/UI/Scheduler/UIxCalListingActions.m @@ -649,7 +649,7 @@ _userStateInEvent (NSArray *event) withNumber: (NSNumber *) number { int currentDayStart, startSecs, endsSecs, currentStart, eventStart, - eventEnd, offset, recurrenceTime; + eventEnd, offset, recurrenceTime, swap; NSMutableArray *currentDay; NSMutableDictionary *eventBlock; iCalPersonPartStat userState; @@ -667,8 +667,13 @@ _userStateInEvent (NSArray *event) else { if (eventEnd < eventStart) - [self warnWithFormat: @"event '%@' has end < start: %d < %d", - [event objectAtIndex: 0], eventEnd, eventStart]; + { + swap = eventStart; + eventStart = eventEnd; + eventEnd = swap; + [self warnWithFormat: @"event '%@' has end < start: %d < %d", + [event objectAtIndex: 0], eventEnd, eventStart]; + } startSecs = (unsigned int) [startDate timeIntervalSince1970]; endsSecs = (unsigned int) [endDate timeIntervalSince1970]; diff --git a/UI/Scheduler/UIxOccurenceDialog.m b/UI/Scheduler/UIxOccurenceDialog.m index 626cde32b..1a573f71e 100644 --- a/UI/Scheduler/UIxOccurenceDialog.m +++ b/UI/Scheduler/UIxOccurenceDialog.m @@ -87,6 +87,13 @@ return self; } +- (id ) confirmAdjustmentAction +{ + ASSIGN (action, @"adjust"); + + return self; +} + - (WOResponse *) deleteAction { SOGoCalendarComponent *component; diff --git a/UI/Scheduler/product.plist b/UI/Scheduler/product.plist index d318e61e6..e3a88736e 100644 --- a/UI/Scheduler/product.plist +++ b/UI/Scheduler/product.plist @@ -232,9 +232,14 @@ }; delegate = { protectedBy = "RespondToComponent"; - actionClass = "UIxAppointmentEditor"; + pageName = "UIxAppointmentEditor"; actionName = "delegate"; }; + adjust = { + protectedBy = "ModifyComponent"; + actionClass = "UIxAppointmentActions"; + actionName = "adjust"; + }; }; }; @@ -283,6 +288,11 @@ protectedBy = "ViewAllComponent"; pageName = "UIxOccurenceDialog"; }; + confirmAdjustment = { + protectedBy = "ViewAllComponent"; + pageName = "UIxOccurenceDialog"; + actionName = "confirmAdjustment"; + }; confirmDeletion = { protectedBy = "Delete Object"; pageName = "UIxOccurenceDialog"; @@ -313,6 +323,11 @@ pageName = "UIxOccurenceDialog"; actionName = "delete"; }; + adjust = { + protectedBy = "ModifyComponent"; + actionClass = "UIxAppointmentActions"; + actionName = "adjust"; + }; }; }; diff --git a/UI/Templates/SchedulerUI/UIxCalDayTable.wox b/UI/Templates/SchedulerUI/UIxCalDayTable.wox index aa77dbb57..4ea971f5d 100644 --- a/UI/Templates/SchedulerUI/UIxCalDayTable.wox +++ b/UI/Templates/SchedulerUI/UIxCalDayTable.wox @@ -50,7 +50,7 @@
diff --git a/UI/Templates/SchedulerUI/UIxCalMainView.wox b/UI/Templates/SchedulerUI/UIxCalMainView.wox index 0c149d000..cf2c48757 100644 --- a/UI/Templates/SchedulerUI/UIxCalMainView.wox +++ b/UI/Templates/SchedulerUI/UIxCalMainView.wox @@ -7,6 +7,7 @@ xmlns:rsrc="OGo:url" xmlns:label="OGo:label" className="UIxPageFrame" + const:jsFiles="SchedulerUIDnD.js" title="title">