#if FRAMEWORK20 using System; using System.Collections.Generic; using DevComponents.Schedule.Model; using System.ComponentModel; namespace DevComponents.DotNetBar.Schedule { internal class ModelWeekDayViewConnector : ModelViewConnector { #region Private variables private CalendarModel _Model; // The associated CalendarModel private WeekDayView _View; // The associated WeekDayView private bool _IsConnected; // Connection status private uint _RefreshCount; #endregion /// /// Constructor /// /// Assoc CalendarModel /// Assoc WeekDayView public ModelWeekDayViewConnector(CalendarModel model, WeekDayView weekDayView) { _Model = model; _View = weekDayView; } #region Public properties /// /// Gets the connection status /// public override bool IsConnected { get { return (_IsConnected); } } #endregion #region Connect processing /// /// Performs Model connection processing /// public override void Connect() { VerifyModel(); if (_IsConnected) Disconnect(); LoadData(); // Get notification on Model property changes _Model.PropertyChanged += ModelPropertyChanged; _Model.SubPropertyChanged += ModelSubPropertyChanged; _View.CalendarView.CustomItems.CollectionChanged += CustomItemsCollectionChanged; _IsConnected = true; } #endregion #region Disconnect processing /// /// Severs the Model/WeekDayView connection /// public override void Disconnect() { VerifyModel(); if (_IsConnected) { // Clear all AllDayPanel items ClearAllDayPanelItems(); // Loop through each DayColumn, clearing each // associated view connection for (int i = 0; i < _View.DayColumns.Length; i++) ClearWeekDayColumn(_View.DayColumns[i]); _View.SubItems.Clear(); // Stop notification on Model property changes _Model.PropertyChanged -= ModelPropertyChanged; _Model.SubPropertyChanged -= ModelSubPropertyChanged; _View.CalendarView.CustomItems.CollectionChanged -= CustomItemsCollectionChanged; _IsConnected = false; OnSubItemsChanged(); } } #region ClearAllDayPanelItems private void ClearAllDayPanelItems() { List items = _View.AllDayPanel.CalendarItems; for (int i = items.Count - 1; i >= 0; i--) { AppointmentWeekDayView view = items[i] as AppointmentWeekDayView; if (view != null) { view.IsSelectedChanged -= _View.ItemIsSelectedChanged; view.Appointment = null; view.IsSelected = false; view.AllDayPanel = null; } items.RemoveAt(i); } _View.AllDayPanel.SubItems.Clear(); } #endregion #region ClearWeekDayColumn /// /// Clears individual DayColumn view connections /// /// DayColumn private void ClearWeekDayColumn(DayColumn dayColumn) { if (dayColumn.CalendarItems.Count > 0) { // Loop through each CalendarItem, resetting // it's associated connection for (int i = dayColumn.CalendarItems.Count - 1; i >= 0; i--) { AppointmentWeekDayView view = dayColumn.CalendarItems[i] as AppointmentWeekDayView; if (view != null) { view.IsSelectedChanged -= _View.ItemIsSelectedChanged; view.Appointment = null; view.IsSelected = false; view.DayColumn = null; } dayColumn.CalendarItems.RemoveAt(i); } } } #endregion #endregion #region LoadData processing /// /// Loads Model/WeekDayView connection data /// private void LoadData() { DayColumn[] dcs = _View.DayColumns; if (dcs.Length > 0) { _RefreshCount++; DateTime startDate = dcs[0].Date; DateTime endDate = DateTimeHelper.EndOfDay(dcs[dcs.Length - 1].Date); DateTime appStartDate = startDate.AddMonths(-1); List appts = GetAppointmentList(_Model, appStartDate, endDate); for (int i = 0; i < dcs.Length; i++) { DayColumn dc = dcs[i]; UpdateColumnAppts(dc, appts); UpdateCustomItems(dc); } UpdateAllDayPanelView(appts, startDate, endDate); UpdateAllDayPanelCustomItems(); OnSubItemsChanged(); } } #region UpdateColumnAppts private void UpdateColumnAppts(DayColumn dayColumn, List appointments) { foreach (Appointment app in appointments) { DateTime date = dayColumn.Date.Date; if (date >= app.StartTime.Date && date <= app.EndTime.Date) { if (IsAppointmentVisible(app)) { // Get the assoc view if (_View.IsAllDayItem(app) == false) { AppointmentWeekDayView view = GetViewFromColumn(dayColumn, app, false) ?? GetViewFromAllDayPanel(app, true) ?? GetNewView(app); if (view.StartTime != app.StartTime || view.EndTime != app.EndTime) dayColumn.NeedRecalcLayout = true; // Set the view start and end times to // match the assoc appointment view.StartTime = app.StartTime; view.EndTime = app.EndTime; view.RefreshCount = _RefreshCount; // Update the DayColumn data if (view.DayColumn == null) { view.DayColumn = dayColumn; dayColumn.CalendarItems.Add(view); dayColumn.NeedRecalcLayout = true; _View.SubItems.Add(view); _View.UpdateItemOrder(view); } } } } } // Update workDay details UpdateWorkDayDetails(dayColumn); } #endregion #region UpdateCustomItems private void UpdateCustomItems(DayColumn dayColumn) { CustomCalendarItemCollection items = _View.CalendarView.CustomItems; if (items != null) { for (int i = 0; i < items.Count; i++) { CustomCalendarItem item = items[i]; if (IsCustomItemVisible(item) == true && _View.IsAllDayItem(item) == false && (item.StartTime < dayColumn.Date.AddDays(1) && item.EndTime > dayColumn.Date)) { item.CalendarView = _View.CalendarView; CustomCalendarItem ci = GetItemFromColumn(dayColumn, item, false); if (ci == null) { ci = GetItemFromAllDayPanel(item, true) ?? GetNewCustomItem(item); dayColumn.CalendarItems.Add(ci); dayColumn.NeedRecalcLayout = true; _View.SubItems.Add(ci); _View.UpdateItemOrder(ci); } ci.StartTime = item.StartTime; ci.EndTime = item.EndTime; ci.RefreshCount = _RefreshCount; dayColumn.NeedRecalcLayout = true; } } } } #endregion #endregion #region RefreshData processing /// /// Refreshes the data in a previously established /// and loaded connection /// public void RefreshData() { CalendarItem selItem = _View.SelectedItem; LoadData(); List removedViews = null; foreach (DayColumn dc in _View.DayColumns) RemoveOutdatedViews(dc, ref removedViews); RemoveOutdatedAllDayViews(ref removedViews); ProcessRemovedData(removedViews); if (selItem != null) { selItem.IsSelected = false; selItem.IsSelected = true; } } #region RemoveOutdatedViews private void RemoveOutdatedViews( DayColumn dayColumn, ref List removedViews) { for (int i = dayColumn.CalendarItems.Count - 1; i >= 0; i--) { CalendarItem view = dayColumn.CalendarItems[i]; if (view != null) { if (view.RefreshCount != _RefreshCount) { if (removedViews == null) removedViews = new List(); removedViews.Add(view); _View.SubItems._Remove(view); _View.NeedRecalcSize = true; dayColumn.CalendarItems.Remove(view); } } } } #endregion #region RemoveOutdatedAllDayViews private void RemoveOutdatedAllDayViews(ref List removedViews) { for (int i = _View.AllDayPanel.CalendarItems.Count - 1; i >= 0; i--) { CalendarItem view = _View.AllDayPanel.CalendarItems[i] as CalendarItem; if (view != null) { if (view.RefreshCount != _RefreshCount || _View.IsAllDayItem(view) == false) { if (removedViews == null) removedViews = new List(); removedViews.Add(view); _View.AllDayPanel.CalendarItems.RemoveAt(i); _View.AllDayPanel.SubItems.Remove(view); _View.NeedRecalcLayout = true; } } } } #endregion #region ProcessRemovedData private void ProcessRemovedData(List removedViews) { if (removedViews != null && removedViews.Count > 0) { for (int i = 0; i < removedViews.Count; i++) { CalendarItem item = removedViews[i]; item.IsSelectedChanged -= _View.ItemIsSelectedChanged; item.Dispose(); } _View.NeedRecalcLayout = true; } } #endregion #endregion #region UpdateAllDayPanelView private void UpdateAllDayPanelView( List appts, DateTime startDate, DateTime endDate) { // Loop through each appointment // updating the assoc view accordingly foreach (Appointment app in appts) { if (app.StartTime < endDate && app.EndTime > startDate) { if (IsAppointmentVisible(app)) { // Get the assoc view if (_View.IsAllDayItem(app) == true) { AppointmentWeekDayView view = GetViewFromAllColumns(app, true) ?? GetViewFromAllDayPanel(app, false) ?? GetNewView(app); // Set the view start and end times to // match the assoc appointment view.StartTime = app.StartTime; view.EndTime = app.EndTime; view.RefreshCount = _RefreshCount; if (view.AllDayPanel == null) { view.AllDayPanel = _View.AllDayPanel; _View.AllDayPanel.CalendarItems.Add(view); _View.AllDayPanel.SubItems.Add(view); _View.NeedRecalcLayout = true; } } } } } } #endregion #region UpdateAllDayPanelCustomItems private void UpdateAllDayPanelCustomItems() { CustomCalendarItemCollection items = _View.CalendarView.CustomItems; if (items != null) { DateTime startDate = _View.StartDate; DateTime endDate = _View.EndDate.AddDays(1); for (int i = 0; i < items.Count; i++) { CustomCalendarItem item = items[i]; if (IsCustomItemVisible(item) == true && _View.IsAllDayItem(item) == true && (item.StartTime < endDate && item.EndTime > startDate)) { item.CalendarView = _View.CalendarView; CustomCalendarItem ci = GetItemFromAllDayPanel(item, false); if (ci == null) { ci = GetItemFromAllColumns(item, true); if (ci == null) ci = GetNewCustomItem(item); _View.AllDayPanel.CalendarItems.Add(ci); _View.NeedRecalcLayout = true; _View.AllDayPanel.SubItems.Add(ci); } if (ci.StartTime != item.StartTime || ci.EndTime != item.EndTime) { ci.StartTime = item.StartTime; ci.EndTime = item.EndTime; _View.NeedRecalcLayout = true; } } } } } #endregion #region UpdateWorkDayDetails /// /// Updates DayColumn workday details /// /// DayColumn to update private void UpdateWorkDayDetails(DayColumn dayColumn) { // Update workDay timings Owner owner = _Model.Owners[_View.OwnerKey]; if (owner == null || GetCalendarWorkDays(dayColumn, owner.CalendarWorkDays) == false) { if (GetCalendarWorkDays(dayColumn, _Model.CalendarWorkDays) == false) { if (owner == null || GetWorkDays(dayColumn, owner.WorkDays) == false) { if (GetWorkDays(dayColumn, _Model.WorkDays) == false) { dayColumn.WorkStartTime = new WorkTime(); dayColumn.WorkEndTime = new WorkTime(); } } } } } #region GetCalendarWorkDays /// /// GetCalendarWorkDays /// /// /// /// private bool GetCalendarWorkDays( DayColumn dayColumn, CalendarWorkDayCollection calendarWorkDays) { if (calendarWorkDays != null && calendarWorkDays.Count > 0) { CalendarWorkDay cwd = calendarWorkDays[dayColumn.Date]; if (cwd != null) { dayColumn.WorkStartTime = cwd.WorkStartTime; dayColumn.WorkEndTime = cwd.WorkEndTime; return (true); } } return (false); } #endregion #region GetWorkDays /// /// GetWorkDays /// /// /// /// private bool GetWorkDays( DayColumn dayColumn, WorkDayCollection workDays) { if (workDays != null && workDays.Count > 0) { WorkDay wd = workDays[dayColumn.Date.DayOfWeek]; if (wd != null) { dayColumn.WorkStartTime = wd.WorkStartTime; dayColumn.WorkEndTime = wd.WorkEndTime; } else { dayColumn.WorkStartTime = new WorkTime(); dayColumn.WorkEndTime = new WorkTime(); } return (true); } return (false); } #endregion #endregion #region GetView routines #region GetViewFromAll private AppointmentWeekDayView GetViewFromAll(Appointment app, bool remove) { AppointmentWeekDayView view = GetViewFromAllColumns(app, remove); if (view != null) return (view); return (GetViewFromAllDayPanel(app, remove)); } #endregion #region GetViewFromAllColumns private AppointmentWeekDayView GetViewFromAllColumns(Appointment app, bool remove) { for (int i = 0; i < _View.NumberOfColumns; i++) { AppointmentWeekDayView view = GetViewFromColumn(_View.DayColumns[i], app, remove); if (view != null) return (view); } return (null); } #endregion #region GetViewFromColumn private AppointmentWeekDayView GetViewFromColumn(DayColumn dayColumn, Appointment appointment, bool remove) { foreach (CalendarItem item in dayColumn.CalendarItems) { AppointmentWeekDayView view = item as AppointmentWeekDayView; if (view != null && view.Appointment == appointment) { if (remove == true) { dayColumn.CalendarItems.Remove(view); _View.SubItems.Remove(view); view.DayColumn = null; } return (view); } } return (null); } #endregion #region GetViewFromAllDayPanel private AppointmentWeekDayView GetViewFromAllDayPanel(Appointment appointment, bool remove) { foreach (CalendarItem item in _View.AllDayPanel.CalendarItems) { AppointmentWeekDayView view = item as AppointmentWeekDayView; if (view != null && view.Appointment == appointment) { if (remove == true) { _View.AllDayPanel.CalendarItems.Remove(view); _View.AllDayPanel.SubItems.Remove(view); view.AllDayPanel = null; } return (view); } } return (null); } #endregion #endregion #region GetItem routines #region GetItemFromColumn private CustomCalendarItem GetItemFromColumn(DayColumn dayColumn, CustomCalendarItem item, bool remove) { foreach (CalendarItem citem in dayColumn.CalendarItems) { CustomCalendarItem view = citem as CustomCalendarItem; if (view != null && (view == item || view.BaseCalendarItem == item)) { if (remove == true) dayColumn.CalendarItems.Remove(view); return (view); } } return (null); } #endregion #region GetItemFromAllColumns private CustomCalendarItem GetItemFromAllColumns(CustomCalendarItem item, bool remove) { for (int i = 0; i < _View.NumberOfColumns; i++) { CustomCalendarItem view = GetItemFromColumn(_View.DayColumns[i], item, false); if (view != null) return (view); } return (null); } #endregion #region GetItemFromAllDayPanel private CustomCalendarItem GetItemFromAllDayPanel(CustomCalendarItem item, bool remove) { foreach (CalendarItem citem in _View.AllDayPanel.CalendarItems) { CustomCalendarItem view = citem as CustomCalendarItem; if (view != null && (view == item || view.BaseCalendarItem == item)) { if (remove == true) _View.AllDayPanel.CalendarItems.Remove(view); return (view); } } return (null); } #endregion #endregion #region GetNewView /// /// Gets a new appointment view /// /// Appointment /// New view private AppointmentWeekDayView GetNewView(Appointment appointment) { AppointmentWeekDayView view = new AppointmentWeekDayView(_View, appointment); view.Tooltip = appointment.Tooltip; view.IsSelectedChanged += _View.ItemIsSelectedChanged; return (view); } #endregion #region GetNewCustomItem private CustomCalendarItem GetNewCustomItem(CustomCalendarItem item) { CustomCalendarItem ci = (CustomCalendarItem)item.Copy(); ci.BaseCalendarItem = item; ci.IsSelectedChanged += _View.ItemIsSelectedChanged; return (ci); } #endregion #region View support routines /// /// Returns the view /// /// public override eCalendarView GetView() { return (eCalendarView.Week); } /// /// Verifies the Model and MonthView are valid /// private void VerifyModel() { if (_Model == null) throw new NullReferenceException("CalendarModel must be set on connector."); if (_View == null) throw new NullReferenceException("WeekDayCalendarView must be set on connector."); } #endregion #region Model property change processing /// /// Handles Model property change notifications /// /// /// private void ModelPropertyChanged(object sender, PropertyChangedEventArgs e) { if (e.PropertyName == CalendarModel.AppointmentsPropertyName) { RefreshData(); UpdateDisplay(); } else if (e.PropertyName == CalendarModel.WorkDaysPropertyName) { for (int i = 0; i < _View.NumberOfColumns; i++) UpdateWorkDayDetails(_View.DayColumns[i]); _View.CalendarView.CalendarPanel.RecalcSize(); } } #endregion #region ModelSubPropertyChanged /// /// Handles ModelSubProperty change notifications /// /// object /// SubPropertyChangedEventArgs private void ModelSubPropertyChanged(object sender, SubPropertyChangedEventArgs e) { if (e.Source is WorkDay) { for (int i = 0; i < _View.NumberOfColumns; i++) UpdateWorkDayDetails(_View.DayColumns[i]); _View.CalendarView.CalendarPanel.RecalcSize(); } else if (e.Source is Owner) { Owner owner = (Owner) e.Source; if (_View.OwnerKey != null && _View.OwnerKey.Equals(owner.Key)) { if (e.PropertyChangedArgs.PropertyName == Owner.DisplayNamePropertyName) _View.DisplayName = owner.DisplayName; else if (e.PropertyChangedArgs.PropertyName.Equals("ColorScheme")) _View.CalendarColor = owner.ColorScheme; } } else if (e.Source is Appointment) { Appointment app = e.Source as Appointment; AppointmentWeekDayView appView; string name = e.PropertyChangedArgs.PropertyName; if (name.Equals("Tooltip")) { appView = GetViewFromAll(app, false); if (appView != null) appView.Tooltip = app.Tooltip; } else if (name.Equals("IsSelected")) { appView = GetViewFromAll(app, false); if (appView != null) appView.IsSelected = app.IsSelected; } else if (name.Equals("CategoryColor") || name.Equals("TimeMarkedAs") || name.Equals("ImageKey")) { appView = GetViewFromAll(app, false); if (appView != null) appView.Refresh(); } else if (name.Equals("OwnerKey")) { if (_View.CalendarView.IsMultiCalendar == true) { if (_View.OwnerKey == app.OwnerKey) { RefreshData(); UpdateDisplay(); } else { appView = GetViewFromAll(app, false); if (appView != null) { RefreshData(); UpdateDisplay(); } } } } else if (name.Equals("Visible")) { RefreshData(); UpdateDisplay(); } } } #endregion #region CustomItems_CollectionChanged void CustomItemsCollectionChanged(object sender, EventArgs e) { RefreshData(); UpdateDisplay(); } #endregion #region UpdateDisplay private void UpdateDisplay() { if (_View.Displayed == true) { if (_View.NeedRecalcLayout == false) { for (int i = 0; i < _View.NumberOfColumns; i++) { if (_View.DayColumns[i].NeedRecalcLayout) { _View.RecalcSize(); break; } } } } } #endregion #region OnSubItemsChanged private void OnSubItemsChanged() { System.Windows.Forms.Cursor.Position = System.Windows.Forms.Cursor.Position; } #endregion } } #endif