DayView.js 17 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470
  1. MWF.xApplication.Meeting.DayView = new Class({
  2. Extends: MWF.widget.Common,
  3. Implements: [Options, Events],
  4. options: {
  5. "style": "default",
  6. "date": null
  7. },
  8. initialize: function(node, app, options){
  9. this.setOptions(options);
  10. this.path = "/x_component_Meeting/$DayView/";
  11. this.cssPath = "/x_component_Meeting/$DayView/"+this.options.style+"/css.wcss";
  12. this._loadCss();
  13. this.app = app;
  14. this.container = $(node);
  15. this.date = this.options.date || new Date();
  16. this.load();
  17. },
  18. load: function(){
  19. this.node = new Element("div", {"styles": this.css.node}).inject(this.container);
  20. this.dayNodeA = new Element("div", {"styles": this.css.dayAreaNode}).inject(this.node);
  21. this.dayNodeB = new Element("div", {"styles": this.css.dayAreaNode}).inject(this.node);
  22. this.dayNodeC = new Element("div", {"styles": this.css.dayAreaNode}).inject(this.node);
  23. this.resetNodeSize();
  24. this.app.addEvent("resize", this.resetNodeSize.bind(this));
  25. //this.dateNode = new Element("div", {"styles": this.css.dateNode}).inject(this.node);
  26. this.loadCalendar();
  27. },
  28. resetNodeSize: function(){
  29. var size = this.container.getSize();
  30. if (this.app.meetingConfig.hideMenu=="static"){
  31. var y = size.y-120;
  32. this.node.setStyle("height", ""+y+"px");
  33. this.node.setStyle("margin-top", "60px");
  34. }else{
  35. var y = size.y-20;
  36. this.node.setStyle("height", ""+y+"px");
  37. }
  38. //var size = this.container.getSize();
  39. //var y = size.y-20;
  40. //this.node.setStyle("height", ""+y+"px");
  41. var dayx = size.x/3
  42. this.dayNodeA.setStyle("width", ""+dayx+"px");
  43. this.dayNodeB.setStyle("width", ""+dayx+"px");
  44. this.dayNodeC.setStyle("width", ""+dayx+"px");
  45. },
  46. toDay: function(date){
  47. this.date = date;
  48. if (this.currentDocument) this.currentDocument.closeDocument();
  49. this.dayA.destroy();
  50. this.dayB.destroy();
  51. this.dayC.destroy();
  52. this.loadCalendar();
  53. },
  54. loadCalendar: function(){
  55. if (!this.date) this.date = new Date();
  56. var date = this.date.clone();
  57. this.dayA = new MWF.xApplication.Meeting.DayView.Calendar(this, this.dayNodeA, date);
  58. date.increment();
  59. this.dayB = new MWF.xApplication.Meeting.DayView.Calendar(this, this.dayNodeB, date);
  60. date.increment();
  61. this.dayC = new MWF.xApplication.Meeting.DayView.Calendar(this, this.dayNodeC, date);
  62. this.dayA.loadAction();
  63. },
  64. hide: function(){
  65. var fx = new Fx.Morph(this.node, {
  66. "duration": "300",
  67. "transition": Fx.Transitions.Expo.easeOut
  68. });
  69. fx.start({
  70. "opacity": 0
  71. }).chain(function(){
  72. this.node.setStyle("display", "none");
  73. }.bind(this));
  74. },
  75. show: function(){
  76. this.node.setStyles(this.css.node);
  77. var fx = new Fx.Morph(this.node, {
  78. "duration": "800",
  79. "transition": Fx.Transitions.Expo.easeOut
  80. });
  81. this.app.fireAppEvent("resize");
  82. fx.start({
  83. "opacity": 1,
  84. "left": "0px"
  85. }).chain(function(){
  86. this.node.setStyles({
  87. "position": "static",
  88. "width": "auto"
  89. });
  90. }.bind(this));
  91. },
  92. reload: function(){
  93. this.dayA.destroy();
  94. this.dayB.destroy();
  95. this.dayC.destroy();
  96. this.loadCalendar();
  97. }
  98. });
  99. MWF.xApplication.Meeting.DayView.Calendar = new Class({
  100. Implements: [Events],
  101. initialize: function(view, node, date){
  102. this.view = view
  103. this.css = this.view.css;
  104. this.container = node;
  105. this.app = this.view.app;
  106. this.date = (date) ? date.clone().clearTime() : (new Date()).clearTime();
  107. this.today = new Date().clearTime();
  108. this.isToday = (this.date.diff(this.today)==0);
  109. this.times = [];
  110. this.meetings = [];
  111. this.load();
  112. },
  113. load: function(){
  114. this.node = new Element("div", {"styles": this.css.dayNode}).inject(this.container);
  115. this.titleNode = new Element("div", {"styles": this.css.dayTitleNode}).inject(this.node);
  116. this.titleDateNode = new Element("div", {"styles": this.css.dayTitleDateNode}).inject(this.node);
  117. if (this.isToday) this.titleDateNode.setStyles(this.css.dayTitleDateNode_today);
  118. this.timeAreaNode = new Element("div", {"styles": this.css.dayTimeAreaNode}).inject(this.node);
  119. this.timeContentNode = new Element("div", {"styles": this.css.dayTimeContentNode}).inject(this.timeAreaNode);
  120. this.setTimeAreaSize();
  121. this.setTimeAreaSizeFun = this.setTimeAreaSize.bind(this);
  122. this.app.addEvent("resize", this.setTimeAreaSizeFun);
  123. this.loadContent();
  124. },
  125. loadAction: function(){
  126. this.downNode = new Element("div", {"styles": this.css.dayTitleDownNode}).inject(this.titleNode);
  127. this.titleNode.setStyle("cursor", "pointer");
  128. this.setActionEvent(this.titleNode);
  129. this.setActionEvent(this.downNode);
  130. this.titleNode.set("value", this.date.format("db"));
  131. },
  132. setActionEvent: function(node){
  133. node.addEvents({
  134. "mouseover": function(){
  135. this.titleNode.setStyles(this.css.dayTitleNode_over);
  136. this.downNode.setStyles(this.css.dayTitleDownNode_over);
  137. }.bind(this),
  138. "mouseout": function(){
  139. this.titleNode.setStyles(this.css.dayTitleNode);
  140. this.downNode.setStyles(this.css.dayTitleDownNode);
  141. }.bind(this),
  142. "mousedown": function(){
  143. this.titleNode.setStyles(this.css.dayTitleNode_down);
  144. this.downNode.setStyles(this.css.dayTitleDownNode_down);
  145. }.bind(this),
  146. "mouseup": function(){
  147. this.titleNode.setStyles(this.css.dayTitleNode_over);
  148. this.downNode.setStyles(this.css.dayTitleDownNode_over);
  149. }.bind(this)
  150. });
  151. MWF.require("MWF.widget.Calendar", function(){
  152. new MWF.widget.Calendar(this.titleNode, {
  153. "style":"meeting",
  154. "target": this.node,
  155. "onQueryComplate": function(e, dv, date){
  156. var selectedDate = new Date.parse(dv);
  157. this.view.toDay(selectedDate);
  158. }.bind(this)
  159. });
  160. }.bind(this));
  161. },
  162. setTimeAreaSize: function(){
  163. var size = this.node.getSize();
  164. var titleSize = this.titleNode.getSize();
  165. var titleDateSize = this.titleDateNode.getSize();
  166. var y = size.y-titleSize.y-titleDateSize.y;
  167. this.timeAreaNode.setStyle("height", ""+y+"px");
  168. },
  169. loadContent: function(){
  170. this.loadTitle();
  171. this.loadTimes();
  172. this.loadMeetings();
  173. },
  174. loadTitle: function(){
  175. var week = this.app.lp.weeks.arr[this.date.getDay()];
  176. var title = "";
  177. var now = this.today;
  178. var d = now.diff(this.date);
  179. if (d==0){
  180. title = this.app.lp.today;
  181. }else if (d==1){
  182. title = this.app.lp.tomorrow
  183. }else if (d==2){
  184. title = this.app.lp.afterTomorrow
  185. }else if (d==-1){
  186. title = this.app.lp.yesterday
  187. }else if (d==-2){
  188. title = this.app.lp.beforeYesterday
  189. }else{
  190. title = week;
  191. }
  192. this.titleNode.set("text", title);
  193. this.titleDateNode.set("text", this.date.format(this.app.lp.dateFormatDay)+" "+week);
  194. },
  195. loadTimes: function(){
  196. this.timeTitleAreaNode = new Element("div", {"styles": this.css.timeTitleAreaNode}).inject(this.timeContentNode);
  197. this.timeBodyAreaNode = new Element("div", {"styles": this.css.timeBodyAreaNode}).inject(this.timeContentNode);
  198. for (var h=0; h<24; h++){
  199. var date = this.date.clone();
  200. date.set("hr", h);
  201. date.set("min", 0);
  202. date.set("sec", 0);
  203. date.set("ms", 0);
  204. this.times.push(new MWF.xApplication.Meeting.DayView.Calendar.Hour(this, date));
  205. }
  206. },
  207. loadMeetings: function(){
  208. var y = this.date.getFullYear();
  209. var m = this.date.getMonth()+1;
  210. var d = this.date.getDate();
  211. this.app.actions.listMeetingDay(y, m, d, function(json){
  212. json.data.each(function(meeting, i){
  213. if (!meeting.myReject){
  214. this.meetings.push(new MWF.xApplication.Meeting.DayView.Calendar.Meeting(this, meeting));
  215. }
  216. }.bind(this));
  217. this.checkMeetingWidth();
  218. this.checkMeetingWidthFun = this.checkMeetingWidth.bind(this);
  219. this.app.addEvent("resize", this.checkMeetingWidthFun);
  220. }.bind(this));
  221. },
  222. checkMeetingWidth: function(){
  223. this.meetings.each(function(meeting){
  224. var timeBodysize = this.timeBodyAreaNode.getSize();
  225. var w = (timeBodysize.x/meeting.intersectionCount)-1;
  226. meeting.node.setStyle("width",""+w+"px");
  227. }.bind(this));
  228. },
  229. destroy: function(){
  230. if (this.checkMeetingWidthFun) this.app.removeEvent("resize", this.checkMeetingWidthFun);
  231. this.app.removeEvent("resize", this.setTimeAreaSizeFun);
  232. this.times.each(function(time){
  233. time.destroy();
  234. });
  235. this.meetings.each(function(meeting){
  236. meeting.destroy();
  237. });
  238. this.meetings = [];
  239. this.times = [];
  240. this.node.destroy();
  241. MWF.release(this);
  242. }
  243. });
  244. MWF.xApplication.Meeting.DayView.Calendar.Meeting = new Class({
  245. initialize: function(day, data){
  246. this.day = day
  247. this.view = this.day.view
  248. this.css = this.view.css;
  249. this.app = this.view.app;
  250. this.data = data;
  251. this.beginDate = Date.parse(this.data.startTime);
  252. this.endDate = Date.parse(this.data.completedTime);
  253. this.load();
  254. },
  255. load: function(){
  256. this.node = new Element("div", {"styles": this.css.meetingNode});
  257. this.colorNode = new Element("div", {"styles": this.css.meetingColorNode}).inject(this.node);
  258. this.contentNode = new Element("div", {"styles": this.css.meetingContentNode}).inject(this.node);
  259. this.subjectNode = new Element("div", {"styles": this.css.meetingSubjectNode}).inject(this.contentNode);
  260. //this.descriptionNode = new Element("div", {"styles": this.css.meetingSubjectNode}).inject(this.node);
  261. this.subjectNode.set("text", this.data.subject);
  262. switch (this.data.status){
  263. case "wait":
  264. //nothing
  265. break;
  266. case "processing":
  267. this.colorNode.setStyles({"background-color": "#18da14"});
  268. this.contentNode.setStyles({"background-color": "#deffdd"});
  269. break
  270. case "completed":
  271. //add attachment
  272. this.colorNode.setStyles({"background-color": "#555"});
  273. this.subjectNode.setStyles({"color": "#666"});
  274. break;
  275. }
  276. if (this.data.myWaitAccept){
  277. this.colorNode.setStyles({"background-color": "#ecd034"});
  278. this.contentNode.setStyles({"background-color": "#fffade"});
  279. }
  280. this.positionNode();
  281. this.checkMax();
  282. this.node.addEvents({
  283. "mouseover": function(){this.node.setStyles(this.css.meetingNode_over);}.bind(this),
  284. "mouseout": function(){this.node.setStyles(this.css.meetingNode);}.bind(this),
  285. "mousedown": function(){this.node.setStyles(this.css.meetingNode_down);}.bind(this),
  286. "mouseup": function(){this.node.setStyles(this.css.meetingNode_over);}.bind(this),
  287. "click": function(){this.openMeeting();}.bind(this),
  288. });
  289. },
  290. openMeeting: function(){
  291. if (!this.document){
  292. if (this.view.currentDocument) this.view.currentDocument.closeDocument();
  293. this.document = new MWF.xApplication.Meeting.DayView.Calendar.Meeting.Document(this);
  294. this.view.currentDocument = this.document;
  295. }
  296. },
  297. checkMax: function(){
  298. this.prevIntersection = null;
  299. this.intersectionCount = 1;
  300. debugger;
  301. for (var i=this.day.meetings.length-1; i>=0; i--){
  302. var pmt = this.day.meetings[i];
  303. if (this.isIntersection(this.beginDate, this.endDate, pmt.beginDate, pmt.endDate)){
  304. this.prevIntersection = pmt;
  305. break;
  306. }
  307. }
  308. var mt = this;
  309. while (mt.prevIntersection){
  310. this.intersectionCount++;
  311. mt = mt.prevIntersection;
  312. }
  313. if (this.prevIntersection){
  314. if (this.prevIntersection.intersectionCount<this.intersectionCount){
  315. mt = this.prevIntersection;
  316. while (mt){
  317. mt.intersectionCount = this.intersectionCount;
  318. mt = mt.prevIntersection;
  319. }
  320. }
  321. }
  322. },
  323. isIntersection: function(d1,d2,d3,d4) {
  324. var bd1 = d1.clone();
  325. var ed1 = d2.clone();
  326. var bd2 = d3.clone();
  327. var ed2 = d4.clone();
  328. this.expandDateRange(bd1, ed1);
  329. this.expandDateRange(bd2, ed2);
  330. if ((bd1 > bd2) && (bd1 < ed2)) return true;
  331. if ((ed1 > bd2) && (ed1 < ed2)) return true;
  332. if ((bd2 > bd1) && (bd2 < ed1)) return true;
  333. if ((ed2 > bd1) && (ed2 < ed1)) return true;
  334. if ((bd1.diff(bd2, "minute")==0) && (ed1.diff(ed2, "minute")==0)) return true;
  335. return false;
  336. },
  337. expandDateRange: function(bd, ed){
  338. bd.set("min", 0);
  339. bd.set("sec", 0);
  340. bd.set("ms", 0);
  341. ed.set("min", 59);
  342. ed.set("sec", 59);
  343. ed.set("ms", 0);
  344. //ed.increment("hour", 1);
  345. },
  346. positionNode: function(){
  347. var bh = this.beginDate.getHours();
  348. var bm = this.beginDate.getMinutes();
  349. var eh = this.endDate.getHours();
  350. var em = this.endDate.getMinutes();
  351. //this.hours = [];
  352. //for (var i=bh; i<=eh; i++){
  353. // this.hours.push(i);
  354. // this.day.times[i].meetings.push(this);
  355. //}
  356. var m = this.beginDate.diff(this.endDate, "minute");
  357. var y = (m/60)*49;
  358. var marginTop = (bm/60)*49;
  359. this.node.inject(this.day.times[bh].contentNode);
  360. this.node.setStyle("padding-top", ""+marginTop+"px");
  361. if (y>30) this.contentNode.setStyle("height", ""+y+"px");
  362. this.colorNode.setStyle("height", ""+y+"px");
  363. },
  364. destroy: function(){
  365. this.node.destroy();
  366. MWF.release(this);
  367. }
  368. });
  369. MWF.xApplication.Meeting.DayView.Calendar.Meeting.Document = new Class({
  370. Extends: MWF.xApplication.Meeting.MeetingView.Document,
  371. initialize: function(item){
  372. this.item = item;
  373. this.view = this.item.view
  374. this.container = this.view.node;
  375. this.app = this.view.app;
  376. this.path = "/x_component_Meeting/$MeetingView/";
  377. this.cssPath = "/x_component_Meeting/$MeetingView/default/css.wcss";
  378. this._loadCss();
  379. this.app.actions.getMeeting(this.item.data.id, function(json){
  380. this.data = json.data;
  381. this.isEdit = (this.data.applicant == this.app.desktop.session.user.name);
  382. this.load();
  383. }.bind(this));
  384. },
  385. _loadCss: function(){
  386. var key = encodeURIComponent(this.cssPath);
  387. if (MWF.widget.css[key]){
  388. this.css = MWF.widget.css[key];
  389. }else{
  390. var r = new Request.JSON({
  391. url: this.cssPath,
  392. secure: false,
  393. async: false,
  394. method: "get",
  395. noCache: false,
  396. onSuccess: function(responseJSON, responseText){
  397. this.css = responseJSON;
  398. MWF.widget.css[key] = responseJSON;
  399. }.bind(this),
  400. onError: function(text, error){
  401. alert(error + text);
  402. }
  403. });
  404. r.send();
  405. }
  406. }
  407. });
  408. MWF.xApplication.Meeting.DayView.Calendar.Hour = new Class({
  409. initialize: function(day, date){
  410. this.day = day
  411. this.view = this.day.view
  412. this.css = this.view.css;
  413. this.app = this.view.app;
  414. this.date = date;
  415. this.meetings = [];
  416. this.load();
  417. },
  418. load: function(){
  419. this.titleNode = new Element("div", {"styles": this.css.hourTitleNode}).inject(this.day.timeTitleAreaNode);
  420. this.contentNode = new Element("div", {"styles": this.css.hourContentNode}).inject(this.day.timeBodyAreaNode);
  421. this.titleNode.set("text", this.date.getHours());
  422. this.titleNode.addEvent("click", function(){
  423. this.app.addMeeting(this.date, this.date.getHours());
  424. }.bind(this));
  425. },
  426. destroy: function(){
  427. this.titleNode.destroy();
  428. this.contentNode.destroy();
  429. MWF.release(this);
  430. }
  431. });