Categories | Question details Back To List | ||
All day events, aka single day "multiday" events and non-scrolling multiday display I was looking at this post: http://www.dhtmlx.com/docs/products/kb/index.shtml?cat=search&page=1&q=13048&ssr=yes&s=all%20day Which seemed to suggest that one should be able to display a single day multiday event. I've had no luck getting a single day event show as it is taking up the whole day like a multiday event. Is there some way to force the event to do this? Also when I have a multiday event, in the day and week view the area that displays the multiday items scrolls with the hour blocks. This makes no sense as these are all day and should always show. The even larger issue is if I set the scheduler.config.scroll_hour property then the all day event will be hidden until the user actually scrolls the view up, which they'll never think to do. Is there a way to get the multiday items to instead be stuck to the top of the day/week views much like the day of the week text? And can we also force an event to be multiday even if it is on a single day? Would be nice to hide the start/stop time too. Thanks, Tys Answer posted by Alex (support) on Dec 15, 2009 02:07 >> Which seemed to suggest that one should be able to display a single day multiday event. not exactly. It suggests that multiday event can be shown in day and week views, but not to be shown in the month view. The filter_month method sets filter for events in month view. So, the solution is: 1) the necessary events are creates as multi-day (2-day, 3-day - it doesn't matter) 2) these events should have some property to filter by it (holiday in the following example): scheduler.filter_month=function(ev){ Answer posted by Tys von Gaza on Dec 15, 2009 13:43 I solved the first issue by override the following function: scheduler.is_one_day_event=function(ev){ if (ev.all_day == "true") return false; var delta = ev.end_date.getDate()-ev.start_date.getDate(); return ( (!delta || (delta == 1 && !ev.end_date.getHours() && !ev.end_date.getMinutes())) && ev.start_date.getMonth()==ev.end_date.getMonth() && ev.start_date.getFullYear()==ev.end_date.getFullYear()) ; } Next up, figuring out how change the day/week "dhx_multi_day" div to be always on top and not scroll with the hours. Tys Answer posted by Tys von Gaza on Dec 15, 2009 19:14 I got all day events now showing above the scrolling day/week view. I think having it above makes a lot more sense. I've included the functions I've changed in case you guys decide to implement something similar. Maybe my code can help jump start a proper implementation. First I added a new div to the main scheduler_here div called dhx_cal_allday that will contain all the all day events: <div id="scheduler_here" class="dhx_cal_container" style='width:100%; height:100%;'> <div class="dhx_cal_navline"> <div class="dhx_cal_prev_button"> </div> <div class="dhx_cal_next_button"> </div> <div class="dhx_cal_today_button"></div> <div class="dhx_cal_date"></div> <div class="dhx_cal_tab" name="agenda_tab" style="right:280px;"></div> <div class="dhx_cal_tab" name="unit_tab" style="right:215px;"></div> <!-- <div class="dhx_cal_tab" name="day_tab" style="right:210px;"></div> --> <div class="dhx_cal_tab" name="week_tab" style="right:150px;"></div> <div class="dhx_cal_tab" name="month_tab" style="right:85px;"></div> <div class="dhx_cal_tab" name="year_tab" style="right:20px;"></div> </div> <div class="dhx_cal_header"> </div> <div class="dhx_cal_allday"> <div class="dhx_multi_day_icon"></div> <div class="dhx_multi_day"></div> </div> <div class="dhx_cal_data"> </div> </div> Next up I have the follow code in a js file that is loaded after the main scheduler js file and before any extensions: scheduler.set_sizes=function(){ //console.log("set_sizes"); var w = this._x = this._obj.clientWidth; var h = this._y = this._obj.clientHeight; //not-table mode always has scroll - need to be fixed in future var scale_x=this._table_view?0:(this.xy.scale_width+this.xy.scroll_width); var scale_s=this._table_view?-1:this.xy.scale_width; var data_y=this.xy.scale_height+this.xy.nav_height+(this._quirks?-2:0); this.set_xy(this._els["dhx_cal_navline"][0],w,this.xy.nav_height,0,0); this.set_xy(this._els["dhx_cal_header"][0],w-scale_x,this.xy.scale_height,scale_s,this.xy.nav_height+(this._quirks?-1:1)); this.set_xy(this._els["dhx_cal_allday"][0],w-scale_x,this.xy.scale_height,0,this.xy.nav_height+this.xy.nav_height+(this._quirks?-1:0)); var allday = this._els["dhx_cal_allday"][0]; var c1 = this._els["dhx_multi_day"][0]; this.set_xy(c1,w-scale_x,0,this.xy.scale_width,0); var c2 = this._els["dhx_multi_day_icon"][0]; this.set_xy(c2,this.xy.scale_width,0,0,0); allday.style.visibility="hidden"; this.set_xy(this._els["dhx_cal_data"][0],w,h-(data_y+2),0,data_y+2); } scheduler._reset_scale=function(){ //console.log("_reset_scale"); var h=this._els["dhx_cal_header"][0]; var allday=this._els["dhx_cal_allday"][0]; var data = this._els["dhx_cal_data"][0]; var b=this._els["dhx_cal_data"][0]; var c = this.config; h.innerHTML=""; b.innerHTML=""; var str=((c.readonly||(!c.drag_resize))?" dhx_resize_denied":"")+((c.readonly||(!c.drag_move))?" dhx_move_denied":""); if (str) b.className = "dhx_cal_data"+str; this._cols=[]; //store for data section this._colsS={height:0}; this._dy_shift=0; this.set_sizes(); var summ=parseInt(h.style.width); //border delta var left=0; var d,dd,sd,today; dd=this.date[this._mode+"_start"](new Date(this._date.valueOf())); d=sd=this._table_view?scheduler.date.week_start(dd):dd; today=this.date.date_part(new Date()); //reset date in header var ed=scheduler.date.add(dd,1,this._mode); var count = 7; if (!this._table_view){ var count_n = this.date["get_"+this._mode+"_end"]; if (count_n) ed = count_n(dd); count = Math.round((ed.valueOf()-dd.valueOf())/(1000*60*60*24)); } this._min_date=d; this._els["dhx_cal_date"][0].innerHTML=this.templates[this._mode+"_date"](dd,ed,this._mode); for (var i=0; i<count; i++){ this._cols[i]=Math.floor(summ/(count-i)); this._render_x_header(i,left,d,h); if (!this._table_view){ var scales=document.createElement("DIV"); var cls = "dhx_scale_holder" if (d.valueOf()==today.valueOf()) cls = "dhx_scale_holder_now"; scales.className=cls+" "+this.templates.week_date_class(d,today); this.set_xy(scales,this._cols[i]-1,c.hour_size_px*(c.last_hour-c.first_hour),left+this.xy.scale_width+1,0);//-1 for border b.appendChild(scales); } d=this.date.add(d,1,"day") summ-=this._cols[i]; left+=this._cols[i]; this._colsS[i]=(this._cols[i-1]||0)+(this._colsS[i-1]||(this._table_view?0:52)); } this._max_date=d; this._colsS[count]=this._cols[count-1]+this._colsS[count-1]; if (this._table_view) { this._reset_month_scale(b,dd,sd); } else { this._reset_hours_scale(b,dd,sd); if (c.multi_day) { allday.style.visibility="hidden"; } } } scheduler._pre_render_events=function(evs,hold){ //console.log("_pre_render_events"); var hb = this.xy.bar_height; var h_old = this._colsS.heights; var h=this._colsS.heights=[0,0,0,0,0,0,0]; if (!this._table_view) evs=this._pre_render_events_line(evs,hold); //ignore long events for now else evs=this._pre_render_events_table(evs,hold); if (this._table_view){ if (hold) this._colsS.heights = h_old; else { var evl = this._els["dhx_cal_data"][0].firstChild; if (evl.rows){ for (var i=0; i<evl.rows.length; i++){ h[i]++; if ((h[i])*hb > this._colsS.height-hb-2){ //we have overflow, update heights var cells = evl.rows[i].cells; for (var j=0; j < cells.length; j++) { cells[j].childNodes[1].style.height = h[i]*hb+"px"; } h[i]=(h[i-1]||0)+cells[0].offsetHeight; } h[i]=(h[i-1]||0)+evl.rows[i].cells[0].offsetHeight; } h.unshift(0); if (evl.parentNode.offsetHeight<evl.parentNode.scrollHeight && !evl._h_fix){ //we have v-scroll, decrease last day cell for (var i=0; i<evl.rows.length; i++){ var cell = evl.rows[i].cells[6].childNodes[0]; var w = cell.offsetWidth-scheduler.xy.scroll_width+"px"; cell.style.width = w; cell.nextSibling.style.width = w; } evl._h_fix=true; } } else{ if (!evs.length && this._els["dhx_cal_allday"][0].style.visibility == "visible") h[0]=-1; if (evs.length || h[0]==-1){ //shift days to have space for multiday events var childs = evl.parentNode.childNodes; var dh = (h[0]+1)*hb+"px"; // for (var i=0; i<childs.length; i++) // if (this._colsS[i]) // childs[i].style.top="0px"; var last = this._els["dhx_multi_day"][0]; last.style.left = this.xy.scale_width + "px"; last.style.height=dh; last.style.visibility=(h[0]==-1?"hidden":"visible"); last=this._els["dhx_multi_day_icon"][0]; last.style.height=dh; last.style.visibility=(h[0]==-1?"hidden":"visible"); last.className=h[0]?"dhx_multi_day_icon":"dhx_multi_day_icon_small"; var allday = this._els["dhx_cal_allday"][0]; allday.style.visibility=(h[0]==-1?"hidden":"visible"); var data = this._els["dhx_cal_data"][0]; data.style.top = (h[0]==-1?"44":"63") + "px"; //this._dy_shift=(h[0]+1)*hb; } } } } return evs; } scheduler.render_event_bar=function(ev){ var parent; if (this._mode=="month") parent=this._els["dhx_cal_data"][0]; else parent=this._els["dhx_cal_allday"][0]; var x=this._colsS[ev._sday]; var x2=this._colsS[ev._eday]; if (x2==x) x2=this._colsS[ev._eday+1]; var hb = this.xy.bar_height; var y=this._colsS.heights[ev._sweek]+(this._colsS.height?(this.xy.scale_height+2):2)+ev._sorder*hb; var d=document.createElement("DIV"); var cs = ev._timed?"dhx_cal_event_clear":"dhx_cal_event_line"; var cse = scheduler.templates.event_class(ev.start_date,ev.end_date,ev); if (cse) cs=cs+" "+cse; var html='<div event_id="'+ev.id+'" class="'+cs+'" style="position:absolute; top:'+y+'px; left:'+x+'px; width:'+(x2-x-15)+'px;'+(ev._text_style||"")+'">'; if (ev._timed) html+=scheduler.templates.event_bar_date(ev.start_date,ev.end_date,ev); html+=scheduler.templates.event_bar_text(ev.start_date,ev.end_date,ev)+'</div>'; html+='</div>'; d.innerHTML=html; this._rendered.push(d.firstChild); parent.appendChild(d.firstChild); } Answer posted by Alex (support) on Dec 16, 2009 02:57 Thank you very much for the provided solution. We'll check it. Answer posted by Tys von Gaza on Dec 16, 2009 08:40 I think I may have a bug in it w/ regards to multiple "all day" events on a single day. Will be checking today. Answer posted by Digo on Dec 17, 2009 05:45 Hi! I am using your solution posted: Dec 15, 2009 13:43 and it works fine in day/month/year view. In agenda-view I get (date-col): 14.Jan 2010 - 13.Jan 2010 <data> <event id="30">
Answer posted by Tys von Gaza on Dec 17, 2009 09:51 Digo, try this: // fix for single day date on agenda scheduler.templates.week_date = function(d1,d2) { if (scheduler.templates.day_date(d1) == scheduler.templates.day_date(d2)) return scheduler.templates.day_date(d1); else return scheduler.templates.day_date(d1)+" – "+scheduler.templates.day_date(scheduler.date.add(d2,-1,"day")); } Answer posted by Digo on Dec 18, 2009 04:12 Hi! Thanks for you answer - works fine! Ciao digo |