/// <summary>
        ///     Splits the over multple days.
        /// </summary>
        /// <param name = "appObj">The app obj.</param>
        /// <returns></returns>
        private static IEnumerable <AppointmentTemporaryObj> SplitOverMultpleDays(AppointmentTemporaryObj appObj)
        {
            var list = new List <AppointmentTemporaryObj>();

            //If Enddate is null or start date matches endate
            if (appObj.EndDate == null || appObj.StartDate == appObj.EndDate)
            {
                list.Add(appObj);
                return(list);
            }
            var dayList = RoomAvailabilityUtilities.ParseDayString(appObj.Days);

            //Iterate over each date in range
            for (var date = appObj.StartDate; date.Date < appObj.EndDate; date = date.AddDays(1))
            {
                //If the current day doesn't exist in the current list of days then continue.
                if (dayList.Count > 0 && !dayList.Contains(date.DayOfWeek))
                {
                    continue;
                }

                //Create new Appoint Temp Obj
                list.Add(new AppointmentTemporaryObj
                {
                    AllDay    = appObj.AllDay,
                    Days      = appObj.Days,
                    EndDate   = date,
                    StartDate = date,
                    StartTime = appObj.StartTime,
                    EndTime   = appObj.EndTime
                });
            }

            return(list);
        }
        /// <summary>
        ///     Overlapses the with.
        /// </summary>
        /// <param name = "a">A.</param>
        /// <param name = "b">The b.</param>
        /// <returns></returns>
        private static bool OverlapsWith(AppointmentTemporaryObj a, AppointmentTemporaryObj b)
        {
            if (b.EndDate == null || a.EndDate == null)
            {
                return(OverlapsWithNoEndDates(a, b));
            }

            return(!(((DateTime)b.EndDate).Add(b.EndTime) <= a.StartDate.Add(a.StartTime) || ((DateTime)a.EndDate).Add(a.EndTime) <= b.StartDate.Add(b.StartTime)));
        }
        /// <summary>
        ///     Processes the date over lap with end date.
        /// </summary>
        /// <param name = "newDate">The new date.</param>
        /// <param name = "currentList">The current list.</param>
        /// <returns></returns>
        private static bool ProcessDateOverLapWithEndDate(AppointmentTemporaryObj newDate, IEnumerable <AppointmentTemporaryObj> currentList)
        {
            var existinglist = new List <AppointmentTemporaryObj>();

            foreach (var date in currentList)
            {
                existinglist.AddRange(SplitOverMultpleDays(date));
            }

            var datetoCheck = new List <AppointmentTemporaryObj>();

            datetoCheck.AddRange(SplitOverMultpleDays(newDate));
            return(datetoCheck.Any(date => GetOverLapList(existinglist, date)));
        }
        /// <summary>
        ///     Overlapses the with no end dates.
        /// </summary>
        /// <param name = "a">A.</param>
        /// <param name = "b">The b.</param>
        /// <returns></returns>
        private static bool OverlapsWithNoEndDates(AppointmentTemporaryObj a, AppointmentTemporaryObj b)
        {
            var aDays       = RoomAvailabilityUtilities.ParseDayString(a.Days);
            var bDays       = RoomAvailabilityUtilities.ParseDayString(b.Days);
            var overLapList = aDays.Where(bDays.Contains).ToList();

            if (overLapList.Count == 0)
            {
                return(false);
            }

            //Compare start time vs end time
            return(!(b.EndTime <= a.StartTime || a.EndTime <= b.StartTime));
        }
        /// <summary>
        ///     Processes the no end date.
        /// </summary>
        /// <param name = "newDate">The new date.</param>
        /// <param name = "currentList">The current list.</param>
        /// <returns></returns>
        private static bool ProcessNoEndDate(AppointmentTemporaryObj newDate, IEnumerable <AppointmentTemporaryObj> currentList)
        {
            //GetItemsWithNoEndDates
            var nonNullDateList = GetItemsWithEndDates(currentList);

            var dateToCheck = newDate;

            dateToCheck.EndDate = ReturnMaxDateInList(nonNullDateList);

            if (dateToCheck.EndDate != null && ProcessDateOverLapWithEndDate(dateToCheck, nonNullDateList))
            {
                return(true);
            }

            var nullDateList = GetItemsWithNoEndDates(currentList);

            return(nullDateList.Any(date => OverlapsWithNoEndDates(newDate, date)));
        }
 /// <summary>
 ///     Gets the over lap list.
 /// </summary>
 /// <param name = "existinglist">The existinglist.</param>
 /// <param name = "date1">The date1.</param>
 /// <returns></returns>
 private static bool GetOverLapList(IEnumerable <AppointmentTemporaryObj> existinglist, AppointmentTemporaryObj date1)
 {
     return((from d in existinglist where OverlapsWith(d, date1) select d).Count() > 0 ? true : false);
 }
 /// <summary>
 ///     Doeses the date over lap.
 /// </summary>
 /// <param name = "newDate">The new date.</param>
 /// <param name = "currentList">The current list.</param>
 /// <returns></returns>
 public static bool DoesDateOverLap(AppointmentTemporaryObj newDate, IEnumerable <AppointmentTemporaryObj> currentList)
 {
     //End Dates Are known
     return(newDate.EndDate != null?ProcessDateOverLapWithEndDate(newDate, currentList) : ProcessNoEndDate(newDate, currentList));
 }
        /// <summary>
        /// Handles the Click event of the _btnAddDates control.
        /// </summary>
        /// <param name="sender">The source of the event.</param>
        /// <param name="e">The <see cref="System.EventArgs"/> instance containing the event data.</param>
        protected void _btnAddDates_Click(object sender, EventArgs e)
        {
            var startDate = (DateTime)_rdpStartDate.DbSelectedDate;
            var startTime = ((DateTime)_rtpStartTime.DbSelectedDate).TimeOfDay;
            var endDate = _rdpEndDate.DbSelectedDate;
            var endTime = ((DateTime)_rtpEndTime.DbSelectedDate).TimeOfDay;

            var days = _rcbDays.CheckedItems.Aggregate(String.Empty, (current, item) => current + (item.Value + ",")).TrimEnd(',');

            var isVald = GetIsValdAddDates(days, endDate, startDate, startTime, endTime);

            if (isVald == false)
                return;

            //Check for any overlap here
            var appointMentToAdd = new AppointmentTemporaryObj
            {
                AllDay = false,
                Days = days,
                EndDate = (DateTime?)endDate,
                EndTime = endTime,
                RoomId = RoomId,
                StartDate = startDate,
                StartTime = startTime
            };

            var db = new UrbanDataContext();
            var currentAvilList = db.Manager.RoomAvailability.GetByRoomID(RoomId).OrderByDescending(t => t.StartDate).ToList();

            //Check if date to add is valid over existing range of dates.
            if (AppointmentTemporaryObj.DoesDateOverLap(appointMentToAdd, currentAvilList.ToAppointmentTempObject()))
            {
                WriteFeedBackMaster(FeedbackType.Error, "Date overlaps");
                return;
            }
            var newAppointment = new RoomAvailability
                                     {
                                         AllDay = appointMentToAdd.AllDay,
                                         Days = appointMentToAdd.Days == String.Empty ? null : appointMentToAdd.Days,
                                         EndDate = appointMentToAdd.EndDate,
                                         EndTime = appointMentToAdd.EndTime,
                                         RoomID = RoomId,
                                         StartDate = appointMentToAdd.StartDate,
                                         StartTime = appointMentToAdd.StartTime
                                     };
            db.RoomAvailability.InsertOnSubmit(newAppointment);
            db.SubmitChanges();
            RebindGridAndScheduler();

        }
        /// <summary>
        ///     Handles the Click event of the _btnAddDates control.
        /// </summary>
        /// <param name = "sender">The source of the event.</param>
        /// <param name = "e">The <see cref = "System.EventArgs" /> instance containing the event data.</param>
        protected void _btnAddDates_Click(object sender, EventArgs e)
        {
            var startDate = (DateTime) _rdpStartDate.DbSelectedDate;
            var startTime = ((DateTime) _rtpStartTime.DbSelectedDate).TimeOfDay;
            var endDate = _rdpEndDate.DbSelectedDate;
            var endTime = ((DateTime) _rtpEndTime.DbSelectedDate).TimeOfDay;

            var days = _rcbDays.CheckedItems.Aggregate(String.Empty, (current, item) => current + (item.Value + ","));
            days = days.TrimEnd(',');


            var isVald = GetIsValdAddDates(days, endDate, startDate, startTime, endTime);

            if (isVald == false)
                return;

            //Check for any overlap here
            var appointMentToAdd = new AppointmentTemporaryObj
                                       {
                                           AllDay = false,
                                           Days = days,
                                           EndDate = (DateTime?) endDate,
                                           EndTime = endTime,
                                           RoomId = 0,
                                           StartDate = startDate,
                                           StartTime = startTime
                                       };

            if (AppointmentTemporaryObj.DoesDateOverLap(appointMentToAdd, AvailabilityList))
            {
                WriteToBothFeedback(FeedbackType.Error, "Date overlaps");
            }
            else
            {
                AvailabilityList.Add(appointMentToAdd);
            }


            _rgAvailableTimes.Rebind();
        }
 /// <summary>
 ///     Gets the over lap list.
 /// </summary>
 /// <param name = "existinglist">The existinglist.</param>
 /// <param name = "date1">The date1.</param>
 /// <returns></returns>
 private static bool GetOverLapList(IEnumerable<AppointmentTemporaryObj> existinglist, AppointmentTemporaryObj date1)
 {
     return (from d in existinglist where OverlapsWith(d, date1) select d).Count() > 0 ? true : false;
 }
        /// <summary>
        ///     Splits the over multple days.
        /// </summary>
        /// <param name = "appObj">The app obj.</param>
        /// <returns></returns>
        private static IEnumerable<AppointmentTemporaryObj> SplitOverMultpleDays(AppointmentTemporaryObj appObj)
        {
            var list = new List<AppointmentTemporaryObj>();

            //If Enddate is null or start date matches endate
            if (appObj.EndDate == null || appObj.StartDate == appObj.EndDate)
            {
                list.Add(appObj);
                return list;
            }
            var dayList = RoomAvailabilityUtilities.ParseDayString(appObj.Days);
            //Iterate over each date in range
            for (var date = appObj.StartDate; date.Date < appObj.EndDate; date = date.AddDays(1))
            {
                //If the current day doesn't exist in the current list of days then continue.
                if (dayList.Count > 0 && !dayList.Contains(date.DayOfWeek))
                    continue;

                //Create new Appoint Temp Obj
                list.Add(new AppointmentTemporaryObj
                             {
                                 AllDay = appObj.AllDay,
                                 Days = appObj.Days,
                                 EndDate = date,
                                 StartDate = date,
                                 StartTime = appObj.StartTime,
                                 EndTime = appObj.EndTime
                             });
            }

            return list;
        }
        /// <summary>
        ///     Processes the date over lap with end date.
        /// </summary>
        /// <param name = "newDate">The new date.</param>
        /// <param name = "currentList">The current list.</param>
        /// <returns></returns>
        private static bool ProcessDateOverLapWithEndDate(AppointmentTemporaryObj newDate, IEnumerable<AppointmentTemporaryObj> currentList)
        {
            var existinglist = new List<AppointmentTemporaryObj>();
            foreach (var date in currentList)
            {
                existinglist.AddRange(SplitOverMultpleDays(date));
            }

            var datetoCheck = new List<AppointmentTemporaryObj>();
            datetoCheck.AddRange(SplitOverMultpleDays(newDate));
            return datetoCheck.Any(date => GetOverLapList(existinglist, date));
        }
        /// <summary>
        ///     Processes the no end date.
        /// </summary>
        /// <param name = "newDate">The new date.</param>
        /// <param name = "currentList">The current list.</param>
        /// <returns></returns>
        private static bool ProcessNoEndDate(AppointmentTemporaryObj newDate, IEnumerable<AppointmentTemporaryObj> currentList)
        {
            //GetItemsWithNoEndDates
            var nonNullDateList = GetItemsWithEndDates(currentList);

            var dateToCheck = newDate;
            dateToCheck.EndDate = ReturnMaxDateInList(nonNullDateList);

            if (dateToCheck.EndDate != null && ProcessDateOverLapWithEndDate(dateToCheck, nonNullDateList))
            {
                return true;
            }

            var nullDateList = GetItemsWithNoEndDates(currentList);
            return nullDateList.Any(date => OverlapsWithNoEndDates(newDate, date));
        }
 /// <summary>
 ///     Doeses the date over lap.
 /// </summary>
 /// <param name = "newDate">The new date.</param>
 /// <param name = "currentList">The current list.</param>
 /// <returns></returns>
 public static bool DoesDateOverLap(AppointmentTemporaryObj newDate, IEnumerable<AppointmentTemporaryObj> currentList)
 {
     //End Dates Are known
     return newDate.EndDate != null ? ProcessDateOverLapWithEndDate(newDate, currentList) : ProcessNoEndDate(newDate, currentList);
 }
        /// <summary>
        ///     Overlapses the with no end dates.
        /// </summary>
        /// <param name = "a">A.</param>
        /// <param name = "b">The b.</param>
        /// <returns></returns>
        private static bool OverlapsWithNoEndDates(AppointmentTemporaryObj a, AppointmentTemporaryObj b)
        {
            var aDays = RoomAvailabilityUtilities.ParseDayString(a.Days);
            var bDays = RoomAvailabilityUtilities.ParseDayString(b.Days);
            var overLapList = aDays.Where(bDays.Contains).ToList();

            if (overLapList.Count == 0)
                return false;

            //Compare start time vs end time
            return !(b.EndTime <= a.StartTime || a.EndTime <= b.StartTime);
        }
        /// <summary>
        ///     Overlapses the with.
        /// </summary>
        /// <param name = "a">A.</param>
        /// <param name = "b">The b.</param>
        /// <returns></returns>
        private static bool OverlapsWith(AppointmentTemporaryObj a, AppointmentTemporaryObj b)
        {
            if (b.EndDate == null || a.EndDate == null)
                return OverlapsWithNoEndDates(a, b);

            return !(((DateTime) b.EndDate).Add(b.EndTime) <= a.StartDate.Add(a.StartTime) || ((DateTime) a.EndDate).Add(a.EndTime) <= b.StartDate.Add(b.StartTime));
        }