source: Scheduling/trunk/cs/bsdx0200GUISourceCode/CalendarGrid.cs@ 1067

Last change on this file since 1067 was 1065, checked in by Sam Habiel, 13 years ago

CalendarGrid: Add MouseEnter event: puts focus on calendar grid. Used to "steal" focus from other controls so that lose focus events would fire.
CGDocumentManager: Added application-wide error handler on Application error exception; Added load timer to test how long it takes to load the GUI.
CGDocument: Just documentation updates.

File size: 55.3 KB
Line 
1namespace IndianHealthService.ClinicalScheduling
2{
3 using System;
4 using System.Collections;
5 using System.ComponentModel;
6 using System.Drawing;
7 using System.Globalization;
8 using System.Runtime.CompilerServices;
9 using System.Runtime.InteropServices;
10 using System.Windows.Forms;
11
12 /// <summary>
13 /// This class is reponsible for rendering the Calendar Grid.
14 /// </summary>
15 public class CalendarGrid : ScrollableControl
16 {
17 private IContainer components;
18 private Font fontArial10;
19 private Font fontArial8;
20 private CGAppointments m_Appointments;
21 private Hashtable m_ApptOverlapTable;
22 private bool m_bAutoDrag = true;
23 private bool m_bDragDropStart;
24 private bool m_bDrawWalkIns = true;
25 private bool m_bGridEnter;
26 private bool m_bInitialUpdate;
27 private bool m_bMouseDown;
28 private bool m_bScroll;
29 private bool m_bScrollDown;
30 private bool m_bSelectingRange;
31 private int m_cellHeight;
32 private int m_cellWidth;
33 private int m_col0Width;
34 private Hashtable m_ColumnInfoTable;
35 private CGCell m_currentCell;
36 private DateTime m_dtStart;
37 private Font m_fCell;
38 private string m_GridBackColor;
39 private CGCells m_gridCells;
40 private int m_nColumns = 5;
41 private int m_nSelectID;
42 private int m_nTimeScale = 20;
43 private ArrayList m_pAvArray;
44 private string m_sDragSource;
45 private CGAppointments m_SelectedAppointments;
46 private CGRange m_selectedRange;
47 private StringFormat m_sf;
48 private StringFormat m_sfHour;
49 private StringFormat m_sfRight;
50 private ArrayList m_sResourcesArray;
51 private Timer m_Timer; // Timeer used in Drag and Drop Operations
52 private ToolTip m_toolTip;
53 private const int WM_HSCROLL = 0x114; // Horizontal Scrolling Windows Message
54 private const int WM_VSCROLL = 0x115; // Vertical Scrolling Windows Message
55
56 public event CGAppointmentChangedHandler CGAppointmentAdded;
57
58 public event CGAppointmentChangedHandler CGAppointmentChanged;
59
60 public event CGSelectionChangedHandler CGSelectionChanged;
61
62 public CalendarGrid()
63 {
64 this.InitializeComponent();
65 base.SetStyle(ControlStyles.AllPaintingInWmPaint, true);
66 base.SetStyle(ControlStyles.UserPaint, true);
67 base.SetStyle(ControlStyles.DoubleBuffer, true);
68 this.m_nColumns = 5;
69 this.m_gridCells = new CGCells();
70 this.m_selectedRange = new CGRange();
71 this.m_SelectedAppointments = new CGAppointments();
72 this.m_dtStart = new DateTime(2003, 1, 27);
73 this.m_ApptOverlapTable = new Hashtable();
74 this.m_ColumnInfoTable = new Hashtable();
75 this.m_sResourcesArray = new ArrayList();
76 base.ResizeRedraw = true;
77 this.m_col0Width = 100;
78 this.fontArial8 = new Font("Arial", 8f);
79 this.fontArial10 = new Font("Arial", 10f);
80 this.m_fCell = this.fontArial10;
81 this.m_sf = new StringFormat();
82 this.m_sfRight = new StringFormat();
83 this.m_sfHour = new StringFormat();
84 this.m_sf.LineAlignment = StringAlignment.Center;
85 this.m_sfRight.LineAlignment = StringAlignment.Center;
86 this.m_sfRight.Alignment = StringAlignment.Far;
87 this.m_sfHour.LineAlignment = StringAlignment.Center;
88 this.m_sfHour.Alignment = StringAlignment.Far;
89 this.m_bInitialUpdate = false;
90 this.MouseEnter += new EventHandler(CalendarGrid_MouseEnter);
91 }
92
93 void CalendarGrid_MouseEnter(object sender, EventArgs e)
94 {
95 this.Focus();
96 }
97
98 private Rectangle AdjustRectForOverlap()
99 {
100 return new Rectangle();
101 }
102
103 private void AutoDragStart()
104 {
105 this.m_bAutoDrag = true;
106 this.m_Timer = new Timer();
107 this.m_Timer.Interval = 5;
108 this.m_Timer.Tick += new EventHandler(this.tickEventHandler);
109 this.m_Timer.Start();
110 }
111
112 private void AutoDragStop()
113 {
114 this.m_bAutoDrag = false;
115 if (this.m_Timer != null)
116 {
117 this.m_Timer.Stop();
118 this.m_Timer.Dispose();
119 this.m_Timer = null;
120 }
121 }
122
123 private void BuildGridCellsArray(Graphics g)
124 {
125 try
126 {
127 SizeF ef = g.MeasureString("Test", this.m_fCell);
128 this.m_cellHeight = ((int) ef.Height) + 4;
129 int nColumns = this.m_nColumns;
130 int num2 = 60 / this.m_nTimeScale;
131 int num3 = 24 * num2;
132 nColumns++;
133 num3++;
134 this.m_cellWidth = 600 / nColumns;
135 if (base.ClientRectangle.Width > 600)
136 {
137 this.m_cellWidth = (base.ClientRectangle.Width - this.m_col0Width) / (nColumns - 1);
138 }
139 if (this.m_nColumns == 1)
140 {
141 this.m_cellWidth = base.ClientRectangle.Width - this.m_col0Width;
142 }
143 g.TranslateTransform((float) base.AutoScrollPosition.X, (float) base.AutoScrollPosition.Y);
144 for (int i = num3; i > -1; i--)
145 {
146 for (int j = 1; j < nColumns; j++)
147 {
148 int x = 0;
149 if (j == 1)
150 {
151 x = this.m_col0Width;
152 }
153 if (j > 1)
154 {
155 x = this.m_col0Width + (this.m_cellWidth * (j - 1));
156 }
157 Point point = new Point(x, i * this.m_cellHeight);
158 Rectangle r = new Rectangle(point.X, point.Y, this.m_cellWidth, this.m_cellHeight);
159 if (i != 0)
160 {
161 CGCell cell = null;
162 cell = new CGCell(r, i, j);
163 this.m_gridCells.AddCell(cell);
164 }
165 }
166 }
167 }
168 catch (Exception exception)
169 {
170 string message = exception.Message;
171 }
172 }
173
174 private void CalendarGrid_DragDrop(object Sender, DragEventArgs e)
175 {
176 CGAppointment data = (CGAppointment) e.Data.GetData(typeof(CGAppointment));
177 Point point = base.PointToClient(new Point(e.X, e.Y));
178 int x = point.X - base.AutoScrollPosition.X;
179 int y = point.Y - base.AutoScrollPosition.Y;
180 Point pt = new Point(x, y);
181 foreach (DictionaryEntry entry in this.m_gridCells.CellHashTable)
182 {
183 CGCell cgCell = (CGCell) entry.Value;
184 if (cgCell.CellRectangle.Contains(pt))
185 {
186 DateTime timeFromCell = this.GetTimeFromCell(cgCell);
187 string resourceFromColumn = this.GetResourceFromColumn(cgCell.CellColumn);
188 int duration = data.Duration;
189 TimeSpan span = new TimeSpan(0, duration, 0);
190 DateTime time2 = timeFromCell + span;
191 data.Selected = false;
192 this.m_nSelectID = 0;
193 CGAppointmentChangedArgs args = new CGAppointmentChangedArgs();
194 args.Appointment = data;
195 args.StartTime = timeFromCell;
196 args.EndTime = time2;
197 args.Resource = resourceFromColumn;
198 args.OldResource = data.Resource;
199 args.AccessTypeID = data.AccessTypeID;
200 args.Slots = data.Slots;
201 if (this.ApptDragSource == "grid")
202 {
203 this.CGAppointmentChanged(this, args);
204 }
205 else
206 {
207 this.CGAppointmentAdded(this, args);
208 }
209 break;
210 }
211 }
212 this.SetOverlapTable();
213 base.Invalidate();
214 }
215
216 private void CalendarGrid_DragEnter(object Sender, DragEventArgs e)
217 {
218 if (e.Data.GetDataPresent(typeof(CGAppointment)))
219 {
220 if ((e.KeyState & 8) == 8)
221 {
222 e.Effect = DragDropEffects.Copy;
223 }
224 else
225 {
226 e.Effect = DragDropEffects.Move;
227 }
228 }
229 else
230 {
231 e.Effect = DragDropEffects.None;
232 }
233 }
234
235 private void CalendarGrid_MouseDown(object sender, MouseEventArgs e)
236 {
237 if (e.Button == MouseButtons.Left)
238 {
239 foreach (DictionaryEntry entry in this.m_gridCells.CellHashTable)
240 {
241 CGCell cell = (CGCell) entry.Value;
242 cell.IsSelected = false;
243 }
244 this.m_selectedRange.Cells.ClearAllCells();
245 this.m_bMouseDown = true;
246 this.OnLButtonDown(e.X, e.Y, true);
247 }
248 }
249
250 private void CalendarGrid_MouseMove(object Sender, MouseEventArgs e)
251 {
252 if (this.m_bMouseDown)
253 {
254 if ((e.Y >= base.ClientRectangle.Bottom) || (e.Y <= base.ClientRectangle.Top))
255 {
256 this.m_bScrollDown = e.Y >= base.ClientRectangle.Bottom;
257 }
258 if ((e.Y < base.ClientRectangle.Bottom) && (e.Y > base.ClientRectangle.Top))
259 {
260 bool bAutoDrag = this.m_bAutoDrag;
261 }
262 if (this.m_bSelectingRange)
263 {
264 this.OnLButtonDown(e.X, e.Y, false);
265 }
266 if (this.m_nSelectID != 0)
267 {
268 if (this.m_bGridEnter)
269 {
270 this.m_bGridEnter = false;
271 }
272 else if (!this.m_bDragDropStart)
273 {
274 CGAppointment data = (CGAppointment) this.m_Appointments.AppointmentTable[this.m_nSelectID];
275 this.ApptDragSource = "grid";
276 base.DoDragDrop(data, DragDropEffects.Move);
277 this.m_bDragDropStart = true;
278 }
279 }
280 }
281 else
282 {
283 int y = e.Y - base.AutoScrollPosition.Y;
284 int x = e.X - base.AutoScrollPosition.X;
285 Point pt = new Point(x, y);
286 foreach (CGAppointment appointment2 in this.m_Appointments.AppointmentTable.Values)
287 {
288 if (appointment2.GridRectangle.Contains(pt))
289 {
290 this.m_toolTip.SetToolTip(this, appointment2.ToString());
291 return;
292 }
293 }
294 this.m_toolTip.RemoveAll();
295
296 ////smh new code -- select cell
297 //int nRow = -1;
298 //int nCol = -1;
299
300 ////Is the mouse over a known cell? If so, highlight cell
301 //if (this.HitTest(x, y, ref nRow, ref nCol))
302 //{
303 // CGCell cellFromRowCol = this.m_gridCells.GetCellFromRowCol(nRow, nCol);
304 // if (cellFromRowCol != null)
305 // {
306 // this.m_currentCell = cellFromRowCol;
307 // this.m_selectedRange.StartCell = null;
308 // this.m_selectedRange.EndCell = null;
309 // this.m_selectedRange.CreateRange(this.m_gridCells, cellFromRowCol, cellFromRowCol);
310 // this.m_bSelectingRange = true;
311 // cellFromRowCol.IsSelected = true;
312 // base.Invalidate(this.m_currentCell.CellRectangle);
313 // //base.Invalidate();
314 // }
315 //}
316
317
318 }
319 }
320
321 private void CalendarGrid_MouseUp(object Sender, MouseEventArgs e)
322 {
323 if (this.m_bAutoDrag)
324 {
325 this.m_bAutoDrag = false;
326 this.AutoDragStop();
327 }
328 this.m_bMouseDown = false;
329 if (this.m_bSelectingRange)
330 {
331 CGSelectionChangedArgs args = new CGSelectionChangedArgs();
332 args.StartTime = this.GetTimeFromCell(this.m_selectedRange.StartCell);
333 args.EndTime = this.GetTimeFromCell(this.m_selectedRange.EndCell);
334 args.Resource = this.GetResourceFromColumn(this.m_selectedRange.StartCell.CellColumn);
335 if (args.EndTime < args.StartTime)
336 {
337 DateTime startTime = args.StartTime;
338 args.StartTime = args.EndTime;
339 args.EndTime = startTime;
340 }
341 TimeSpan span = new TimeSpan(0, 0, this.m_nTimeScale, 0, 0);
342 args.EndTime += span;
343 this.CGSelectionChanged(this, args);
344 this.m_bSelectingRange = false;
345 }
346 }
347
348 private void CalendarGrid_Paint(object sender, PaintEventArgs e)
349 {
350 if (e.Graphics != null)
351 {
352 this.DrawGrid(e.Graphics);
353 if (!this.m_bInitialUpdate)
354 {
355 this.SetAppointmentTypes();
356 base.Invalidate();
357 this.m_bInitialUpdate = true;
358 }
359 }
360 }
361
362 public void CloseGrid()
363 {
364 foreach (CGAppointment appointment in this.m_Appointments.AppointmentTable.Values)
365 {
366 appointment.Selected = false;
367 }
368 this.m_nSelectID = 0;
369 }
370
371 protected override void Dispose(bool disposing)
372 {
373 if (disposing && (this.components != null))
374 {
375 this.components.Dispose();
376 }
377 base.Dispose(disposing);
378 }
379
380 private void DrawAppointments(Graphics g, int col0Width, int cellWidth, int cellHeight)
381 {
382 if (!base.DesignMode && (this.m_Appointments != null))
383 {
384 int num = 0;
385 int num2 = 0;
386 int x = 0;
387 ArrayList list = new ArrayList();
388 foreach (CGAppointment appointment in this.m_Appointments.AppointmentTable.Values)
389 {
390 bool bRet = false;
391 Rectangle rect = this.GetAppointmentRect(appointment, col0Width, cellWidth, cellHeight, out bRet);
392 if (bRet && (!appointment.WalkIn || this.m_bDrawWalkIns))
393 {
394 rect.Inflate(-10, 0);
395 num = (int) this.m_ApptOverlapTable[appointment.m_nKey];
396 num2 = rect.Right - rect.Left;
397 x = num2 / (num + 1);
398 rect.Width = x;
399 if (num > 0)
400 {
401 foreach (object obj2 in list)
402 {
403 Rectangle rectangle2 = (Rectangle) obj2;
404 if (rect.IntersectsWith(rectangle2))
405 {
406 rect.Offset(x, 0);
407 }
408 }
409 }
410 appointment.GridRectangle = rect;
411 if (appointment.Selected)
412 {
413 Pen pen = new Pen(Brushes.Black, 5f);
414 g.DrawRectangle(pen, rect);
415 pen.Dispose();
416 }
417 else
418 {
419 g.DrawRectangle(Pens.Blue, rect);
420 }
421 string s = appointment.ToString();
422 Rectangle rectangle3 = new Rectangle(rect.X + 1, rect.Y + 1, rect.Width - 1, rect.Height - 1);
423 g.FillRectangle(Brushes.White, rectangle3);
424 Brush black = Brushes.Black;
425 if (appointment.CheckInTime.Ticks > 0L)
426 {
427 black = Brushes.Green;
428 g.FillRectangle(Brushes.LightGreen, rectangle3);
429 }
430 if (appointment.NoShow)
431 {
432 black = Brushes.Red;
433 g.FillRectangle(Brushes.LightPink, rectangle3);
434 }
435 if (appointment.WalkIn)
436 {
437 black = Brushes.Blue;
438 g.FillRectangle(Brushes.LightSteelBlue, rectangle3);
439 }
440 g.DrawString(s, this.fontArial8, black, rectangle3);
441 list.Add(rect);
442 }
443 }
444 }
445 }
446
447 private void DrawGrid(Graphics g)
448 {
449 //Default color of grid lines is black
450 Pen pen = new Pen(Color.Black);
451
452 //each cell's height is Height of Arial Font 10pt + 10 pixels (by default 26 pixels)
453 SizeF ef = g.MeasureString("Test", this.m_fCell);
454 int num = 10;
455 this.m_cellHeight = ((int) ef.Height) + num;
456
457 // Number of columns is dynamic based on user of Grid. See Property Columns. Default 5 in init.
458 int nColumns = this.m_nColumns;
459
460 //Time scale is also dynamic. Property TimeScale. Default 20 (minutes)
461 //num3 stands for number of cells per hour
462 int num3 = 60 / this.m_nTimeScale;
463 //num4 stands for number of cells per day (aka rows in the grid)
464 int num4 = 24 * num3;
465 //Add extra column to hold time in the left hand corner
466 nColumns++;
467 //add extra row to represent dates or resources (depending on which view we are in)
468 //Not sure of which variable controls view yet.
469 num4++;
470
471 // 100 px is reserved no matter our column sizes for displaying the time scale
472
473 // Minimum cell width is 600/columns (100 px by default)
474 this.m_cellWidth = 600 / nColumns;
475
476 // if we happen to have more than 600 pixels in our Client Window then cell
477 // is (Width-100) / (number of date columns)
478 if (base.ClientRectangle.Width > 600)
479 {
480 this.m_cellWidth = (base.ClientRectangle.Width - this.m_col0Width) / (nColumns - 1);
481 }
482
483 // If we have one column, the cell width is the itself - 100
484 if (this.m_nColumns == 1)
485 {
486 this.m_cellWidth = base.ClientRectangle.Width - this.m_col0Width;
487 }
488
489 // Our rectangle will start scrolling if width is less than 600 and height less than height of all cells comb
490 // Of course Height will scroll all the time unless you have a humungous screen
491 base.AutoScrollMinSize = new Size(600, this.m_cellHeight * num4);
492
493 // Default Rectangle is Gray
494 g.FillRectangle(Brushes.LightGray, base.ClientRectangle);
495
496 int num5 = 0; //Minutes (start at 0)
497 int num6 = 0; //Hour (starts at 0)
498
499 // flag is true only if there are no cells what so ever in the screen
500 // Only true when no resource is selected.
501 bool flag = this.m_gridCells.CellCount == 0;
502
503 // Move the base point from the client screen to the scrolling region top-left corner.
504 g.TranslateTransform((float) base.AutoScrollPosition.X, (float) base.AutoScrollPosition.Y);
505
506 // This for loop draws the time scale (although I haven't completely traced it out)
507 // For each row except the first one (i starts from 1 rather than zero)
508 for (int i = 1; i < num4; i++)
509 {
510 int x = 0;
511 //point is (0, 1st Cell Start) then (0, 2nd Cell Start) until we run out
512 Point point = new Point(x, i * this.m_cellHeight);
513 //rectangle2 represents each cell rectangle
514 Rectangle rectangle2 = new Rectangle(point.X, point.Y, this.m_cellWidth, this.m_cellHeight);
515 //rect stands for the time scale rectangle; width is 100px; Height is length of the hour on grid
516 Rectangle rect = new Rectangle(0, rectangle2.Y, this.m_col0Width, rectangle2.Height * num3);
517 //height is length of hour
518 int height = rect.Height;
519 //Min font height is 25 pixels (100/4)--see below where it's used
520 height = (height > (this.m_col0Width / 4)) ? (this.m_col0Width / 4) : height;
521
522 //if we are the top of the time scale (at hour:00) -- num5 is min
523 if (num5 == 0)
524 {
525 // Fill time scale triangle with Gray (remember, this is the whole hour!)
526 g.FillRectangle(Brushes.LightGray, rect);
527 // Draw Rectangle
528 g.DrawRectangle(pen, rect.X, rect.Y, rect.Width, rect.Height);
529 //Pad time with at least one zero to make it 2 digits
530 string str = string.Format("{0}", num6).PadLeft(2, '0');
531 //Font height using pixels. Min is 25 pixels
532 Font font = new Font("Arial", (float) height, FontStyle.Bold, GraphicsUnit.Pixel);
533 // rectangle3 is the left half of the time rectangle
534 Rectangle rectangle3 = new Rectangle(rect.X, rect.Y, rect.Width / 2, rect.Height);
535 // In this left half, draw the hours (m_sfHour is the stringformat:
536 // Horizontal Center and Right Justified to rectangle3
537 g.DrawString(str, font, Brushes.Black, rectangle3, this.m_sfHour);
538 // Increment hour
539 num6++;
540 font.Dispose();
541 }
542
543 // Pad minutes with zeros to be 2 digits long
544 string s = string.Format("{0}", num5);
545 s = ":" + s.PadLeft(2, '0');
546 // Rectangle starts at
547 // X: 2/3rds of width of Time Rectangle
548 // Y: Top of the current time slot cell
549 // Width: 1/3rd of the width of the Time Rectangle
550 // Height: Height of a time slot
551 Rectangle layoutRectangle = new Rectangle(rect.X + ((rect.Width * 2) / 3), rectangle2.Top, rect.Width / 3, rectangle2.Height);
552 // At in this rectangle, write the minutes. Horizontal Ctr and Right Justified to Rectangle
553 g.DrawString(s, this.m_fCell, Brushes.Black, layoutRectangle, this.m_sfRight);
554 // Draw Line from two points, just under the time we have just written
555 Point point2 = new Point(rect.X + ((rect.Width * 2) / 3), rectangle2.Bottom);
556 Point point3 = new Point(rect.Right, rectangle2.Bottom);
557 g.DrawLine(pen, point2, point3);
558 // Increment the minutes with the time scale
559 num5 += this.m_nTimeScale;
560 // If miniutes reaches 60, reset to zero
561 num5 = (num5 >= 60) ? 0 : num5;
562 // When we reach the bottom (num4 - 1 is # of rows) and we are not scrolling
563 if ((i == (num4 - 1)) && !this.m_bScroll)
564 {
565 // Fill the last cell with Gray (?)
566 g.TranslateTransform((float) -base.AutoScrollPosition.X, (float) -base.AutoScrollPosition.Y);
567 rect = new Rectangle(0, 0, this.m_col0Width, this.m_cellHeight);
568 g.FillRectangle(Brushes.LightGray, rect);
569 g.DrawRectangle(pen, rect);
570 g.TranslateTransform((float) base.AutoScrollPosition.X, (float) base.AutoScrollPosition.Y);
571 }
572 }
573
574 //This for loop draws the cells
575 //Start from the bottom (num4 is # of rows) and go down to the zeroth row (ie date row/resource row)
576 for (int j = num4; j > -1; j--)
577 {
578 // For each column - 1 (we start at 1, not zero-->We drew the first column anyways in the 1st loop)
579 for (int k = 1; k < nColumns; k++)
580 {
581 int num12 = 0; // X-axis position
582 if (k == 1) // If we are at the first column, start at 100px (default)
583 {
584 num12 = this.m_col0Width;
585 }
586 if (k > 1) //
587 {
588 num12 = this.m_col0Width + (this.m_cellWidth * (k - 1));
589 }
590 Point point4 = new Point(num12, j * this.m_cellHeight);
591 Rectangle r = new Rectangle(point4.X, point4.Y, this.m_cellWidth, this.m_cellHeight);
592 if (j != 0)
593 {
594 CGCell cellFromRowCol = null;
595 if (flag)
596 {
597 cellFromRowCol = new CGCell(r, j, k);
598 this.m_gridCells.AddCell(cellFromRowCol);
599 }
600 else
601 {
602 cellFromRowCol = this.m_gridCells.GetCellFromRowCol(j, k);
603 cellFromRowCol.CellRectangle = r;
604 }
605 if (this.m_sResourcesArray.Count > 0)
606 {
607 if (this.m_selectedRange.CellIsInRange(cellFromRowCol))
608 {
609 g.FillRectangle(Brushes.Aquamarine, r);
610 }
611 else
612 {
613 g.FillRectangle(cellFromRowCol.AppointmentTypeColor, r);
614 }
615 g.DrawRectangle(pen, r.X, r.Y, r.Width, r.Height);
616 if (j == 1)
617 {
618 this.DrawAppointments(g, this.m_col0Width, this.m_cellWidth, this.m_cellHeight);
619 }
620 }
621 continue;
622 }
623 if (!this.m_bScroll)
624 {
625 g.TranslateTransform(0f, (float) -base.AutoScrollPosition.Y);
626 Rectangle rectangle6 = r;
627 g.FillRectangle(Brushes.LightBlue, rectangle6);
628 g.DrawRectangle(pen, rectangle6.X, rectangle6.Y, rectangle6.Width, rectangle6.Height);
629 string str3 = "";
630 if (this.m_sResourcesArray.Count > 1)
631 {
632 foreach (DictionaryEntry entry in this.m_ColumnInfoTable)
633 {
634 int num13 = (int) entry.Value;
635 num13++;
636 if (num13 == k)
637 {
638 str3 = entry.Key.ToString();
639 break;
640 }
641 }
642 }
643 else
644 {
645 DateTime dtStart = this.m_dtStart;
646 if (k > 1)
647 {
648 dtStart = dtStart.AddDays((double) (k - 1));
649 }
650 string format = "ddd, MMM d";
651 str3 = dtStart.ToString(format, DateTimeFormatInfo.InvariantInfo);
652 }
653 g.DrawString(str3, this.m_fCell, Brushes.Black, rectangle6, this.m_sf);
654 g.TranslateTransform(0f, (float) base.AutoScrollPosition.Y);
655 }
656 }
657 }
658 this.m_bScroll = false;
659 pen.Dispose();
660 }
661
662 public Rectangle GetAppointmentRect(CGAppointment a, int col0Width, int cellWidth, int cellHeight, out bool bRet)
663 {
664 DateTime startTime = a.StartTime;
665 DateTime endTime = a.EndTime;
666 string resource = a.Resource;
667 int originX = 0;
668 int originY = 0;
669 int recHeight = 0;
670 int recWidth = 0;
671 int columnToPutAppt = 0;
672 Rectangle rectangle = new Rectangle();
673 int startTotalMinutesoffset = (int) startTime.TimeOfDay.TotalMinutes;
674 int endTotalMinutesoffset = (int) endTime.TimeOfDay.TotalMinutes;
675
676 // To fix a bug with 1 day view: if the start time of appt is before Calendar Start Date, don't draw anything.
677 if (startTime < this.m_dtStart)
678 {
679 bRet = false;
680 return rectangle;
681 }
682
683 // if grid has more than one reource
684 if (this.m_sResourcesArray.Count > 1)
685 {
686 // get zero based index
687 columnToPutAppt = (int) this.m_ColumnInfoTable[resource];
688 // increment to 1 based index
689 columnToPutAppt++;
690 }
691 else
692 {
693 columnToPutAppt = (startTime - this.m_dtStart).Days + 1;
694 }
695 // this if should not get tripped; it did the same function as the new first if check.
696 //if (columnToPutAppt < 1)
697 //{
698 // bRet = false;
699 // return rectangle;
700 //}
701 originX = col0Width + (cellWidth * (columnToPutAppt - 1));
702 int num8 = startTotalMinutesoffset + this.m_nTimeScale;
703 int num9 = (endTotalMinutesoffset > 0) ? endTotalMinutesoffset : 0x5a0;
704 num9 -= startTotalMinutesoffset;
705 originY = (cellHeight * num8) / this.m_nTimeScale;
706 recHeight = (cellHeight * num9) / this.m_nTimeScale;
707 recWidth = cellWidth;
708 rectangle.X = originX;
709 rectangle.Y = originY;
710 rectangle.Width = recWidth;
711 rectangle.Height = recHeight;
712 bRet = true;
713 return rectangle;
714 }
715
716 public bool GetCellFromTime(DateTime dDate, ref int nRow, ref int nCol, bool bStartCell, string sResource)
717 {
718 int num = (dDate.Hour * 60) + dDate.Minute;
719 nRow = num / this.m_nTimeScale;
720 if (bStartCell)
721 {
722 nRow++;
723 }
724 if (this.m_sResourcesArray.Count > 1)
725 {
726 if (sResource == "")
727 {
728 sResource = this.m_sResourcesArray[0].ToString();
729 }
730 nCol = (int) this.m_ColumnInfoTable[sResource];
731 nCol++;
732 return true;
733 }
734 DateTime time = new DateTime(dDate.Year, dDate.Month, dDate.Day);
735 TimeSpan span = (TimeSpan) (time - this.StartDate);
736 int totalDays = 0;
737 totalDays = (int) span.TotalDays;
738 nCol = totalDays;
739 nCol++;
740 return true;
741 }
742
743 private string GetResourceFromColumn(int nCol)
744 {
745 if (this.m_sResourcesArray.Count == 1)
746 {
747 return this.m_sResourcesArray[0].ToString();
748 }
749 foreach (DictionaryEntry entry in this.m_ColumnInfoTable)
750 {
751 int num = (int) entry.Value;
752 num++;
753 if (num == nCol)
754 {
755 return entry.Key.ToString();
756 }
757 }
758 return "";
759 }
760
761 public bool GetSelectedTime(out DateTime dStart, out DateTime dEnd, out string sResource)
762 {
763 if (this.m_selectedRange.Cells.CellCount == 0)
764 {
765 dEnd = new DateTime();
766 dStart = dEnd;
767 sResource = "";
768 return false;
769 }
770 CGCell startCell = this.m_selectedRange.StartCell;
771 CGCell endCell = this.m_selectedRange.EndCell;
772 if (startCell.CellRow > endCell.CellRow)
773 {
774 CGCell cell3 = startCell;
775 startCell = endCell;
776 endCell = cell3;
777 }
778 dStart = this.GetTimeFromCell(startCell);
779 dEnd = this.GetTimeFromCell(endCell);
780 dEnd = dEnd.AddMinutes((double) this.m_nTimeScale);
781 sResource = this.GetResourceFromColumn(startCell.CellColumn);
782 return true;
783 }
784
785 public bool GetSelectedType(out int nAccessTypeID)
786 {
787 nAccessTypeID = 0;
788 if (this.m_selectedRange.Cells.CellCount == 0)
789 {
790 return false;
791 }
792 CGCell startCell = this.m_selectedRange.StartCell;
793 CGCell endCell = this.m_selectedRange.EndCell;
794 if (startCell.CellRow > endCell.CellRow)
795 {
796 CGCell cell3 = startCell;
797 startCell = endCell;
798 endCell = cell3;
799 }
800 DateTime timeFromCell = this.GetTimeFromCell(startCell);
801 DateTime time2 = this.GetTimeFromCell(endCell).AddMinutes((double) this.m_nTimeScale);
802 foreach (CGAvailability availability in this.m_pAvArray)
803 {
804 if (this.TimesOverlap(availability.StartTime, availability.EndTime, timeFromCell, time2))
805 {
806 nAccessTypeID = availability.AvailabilityType;
807 break;
808 }
809 }
810 return (nAccessTypeID > 0);
811 }
812
813 public DateTime GetTimeFromCell(CGCell cgCell)
814 {
815 int cellRow = cgCell.CellRow;
816 int cellColumn = cgCell.CellColumn;
817 DateTime dtStart = this.m_dtStart;
818 int num3 = (cellRow - 1) * this.m_nTimeScale;
819 int num4 = num3 / 60;
820 if (num4 > 0)
821 {
822 num3 = num3 % (num4 * 60);
823 }
824 dtStart = dtStart.AddHours((double) num4).AddMinutes((double) num3);
825 if (this.m_sResourcesArray.Count == 1)
826 {
827 dtStart = dtStart.AddDays((double) (cellColumn - 1));
828 }
829 return dtStart;
830 }
831
832 public bool GetTypeFromCell(CGCell cgCell, out int nAccessTypeID)
833 {
834 nAccessTypeID = 0;
835 CGCell cell = cgCell;
836 CGCell cell2 = cgCell;
837 if (cell.CellRow > cell2.CellRow)
838 {
839 CGCell cell3 = cell;
840 cell = cell2;
841 cell2 = cell3;
842 }
843 DateTime timeFromCell = this.GetTimeFromCell(cell);
844 DateTime time2 = this.GetTimeFromCell(cell2).AddMinutes((double) this.m_nTimeScale);
845 foreach (CGAvailability availability in this.m_pAvArray)
846 {
847 if (this.TimesOverlap(availability.StartTime, availability.EndTime, timeFromCell, time2))
848 {
849 nAccessTypeID = availability.AvailabilityType;
850 break;
851 }
852 }
853 return (nAccessTypeID > 0);
854 }
855
856 private bool HitTest(int X, int Y, ref int nRow, ref int nCol)
857 {
858 Y -= base.AutoScrollPosition.Y;
859 X -= base.AutoScrollPosition.X;
860 foreach (DictionaryEntry entry in this.m_gridCells)
861 {
862 CGCell cell = (CGCell) entry.Value;
863 if (cell.CellRectangle.Contains(X, Y))
864 {
865 nRow = cell.CellRow;
866 nCol = cell.CellColumn;
867 return true;
868 }
869 }
870 return false;
871 }
872
873 public void InitializeCalendarGrid()
874 {
875 this.AllowDrop = true;
876 }
877
878 private void InitializeComponent()
879 {
880 this.components = new System.ComponentModel.Container();
881 this.m_toolTip = new System.Windows.Forms.ToolTip(this.components);
882 this.SuspendLayout();
883 //
884 // CalendarGrid
885 //
886 this.AutoScroll = true;
887 this.AutoScrollMinSize = new System.Drawing.Size(600, 400);
888 this.BackColor = System.Drawing.SystemColors.Window;
889 this.Paint += new System.Windows.Forms.PaintEventHandler(this.CalendarGrid_Paint);
890 this.MouseMove += new System.Windows.Forms.MouseEventHandler(this.CalendarGrid_MouseMove);
891 this.DragDrop += new System.Windows.Forms.DragEventHandler(this.CalendarGrid_DragDrop);
892 this.MouseDown += new System.Windows.Forms.MouseEventHandler(this.CalendarGrid_MouseDown);
893 this.MouseUp += new System.Windows.Forms.MouseEventHandler(this.CalendarGrid_MouseUp);
894 this.DragEnter += new System.Windows.Forms.DragEventHandler(this.CalendarGrid_DragEnter);
895 this.ResumeLayout(false);
896
897 }
898
899 private int MinSince80(DateTime d)
900 {
901 DateTime time = new DateTime(1980, 1, 1, 0, 0, 0);
902 TimeSpan span = (TimeSpan) (d - time);
903 return (int) span.TotalMinutes;
904 }
905
906 private void OnLButtonDown(int X, int Y, bool bStart)
907 {
908 this.m_bDragDropStart = false;
909 this.m_nSelectID = 0;
910 if (!this.m_bSelectingRange)
911 {
912 int y = Y - base.AutoScrollPosition.Y;
913 int x = X - base.AutoScrollPosition.X;
914 Point pt = new Point(x, y);
915 if (Control.ModifierKeys == Keys.Control)
916 {
917 this.m_bMouseDown = false;
918 foreach (CGAppointment appointment in this.m_Appointments.AppointmentTable.Values)
919 {
920 if (!appointment.GridRectangle.Contains(pt))
921 {
922 continue;
923 }
924 if (this.m_SelectedAppointments.AppointmentTable.ContainsKey(appointment.AppointmentKey))
925 {
926 this.m_SelectedAppointments.RemoveAppointment(appointment.AppointmentKey);
927 if (this.m_SelectedAppointments.AppointmentTable.Count == 0)
928 {
929 this.m_nSelectID = 0;
930 }
931 else
932 {
933 foreach (CGAppointment appointment2 in this.m_Appointments.AppointmentTable.Values)
934 {
935 this.m_nSelectID = appointment2.AppointmentKey;
936 }
937 }
938 }
939 else
940 {
941 this.m_SelectedAppointments.AddAppointment(appointment);
942 this.m_nSelectID = appointment.AppointmentKey;
943 }
944 appointment.Selected = !appointment.Selected;
945 break;
946 }
947 base.Invalidate();
948 return;
949 }
950 foreach (CGAppointment appointment3 in this.m_Appointments.AppointmentTable.Values)
951 {
952 if (!appointment3.GridRectangle.Contains(pt))
953 {
954 continue;
955 }
956 this.m_bMouseDown = false;
957 if (appointment3.Selected)
958 {
959 appointment3.Selected = false;
960 this.m_SelectedAppointments.ClearAllAppointments();
961 this.m_nSelectID = 0;
962 }
963 else
964 {
965 foreach (CGAppointment appointment4 in this.m_Appointments.AppointmentTable.Values)
966 {
967 appointment4.Selected = false;
968 }
969 this.m_SelectedAppointments.ClearAllAppointments();
970 this.m_SelectedAppointments.AddAppointment(appointment3);
971 appointment3.Selected = true;
972 this.m_nSelectID = appointment3.AppointmentKey;
973 this.m_bMouseDown = true;
974 this.m_bGridEnter = true;
975 }
976 base.Invalidate();
977 return;
978 }
979 }
980 int nRow = -1;
981 int nCol = -1;
982 if (this.HitTest(X, Y, ref nRow, ref nCol))
983 {
984 CGCell cellFromRowCol = this.m_gridCells.GetCellFromRowCol(nRow, nCol);
985 if (cellFromRowCol != null)
986 {
987 if (bStart)
988 {
989 this.m_currentCell = cellFromRowCol;
990 this.m_selectedRange.StartCell = null;
991 this.m_selectedRange.EndCell = null;
992 this.m_selectedRange.CreateRange(this.m_gridCells, cellFromRowCol, cellFromRowCol);
993 bStart = false;
994 this.m_bMouseDown = true;
995 this.m_bSelectingRange = true;
996 }
997 else if (cellFromRowCol != this.m_currentCell)
998 {
999 if (!this.m_selectedRange.Cells.CellHashTable.ContainsKey(cellFromRowCol.Key))
1000 {
1001 this.m_selectedRange.AppendCell(this.m_gridCells, cellFromRowCol);
1002 }
1003 else
1004 {
1005 bool bUp = cellFromRowCol.CellRow < this.m_currentCell.CellRow;
1006 this.m_selectedRange.SubtractCell(this.m_gridCells, cellFromRowCol, bUp);
1007 }
1008 this.m_currentCell = cellFromRowCol;
1009 }
1010 cellFromRowCol.IsSelected = true;
1011 base.Invalidate();
1012 }
1013 }
1014 }
1015
1016 public void OnUpdateArrays()
1017 {
1018 try
1019 {
1020 this.m_gridCells.ClearAllCells();
1021 this.SetColumnInfo();
1022 this.SetOverlapTable();
1023 Graphics g = base.CreateGraphics();
1024 this.BuildGridCellsArray(g);
1025 this.SetAppointmentTypes();
1026 }
1027 catch (Exception exception)
1028 {
1029 string message = exception.Message;
1030 }
1031 }
1032
1033 private void SetAppointmentTypes()
1034 {
1035 if (this.m_gridCells.CellCount != 0)
1036 {
1037 foreach (DictionaryEntry entry in this.m_gridCells.CellHashTable)
1038 {
1039 CGCell cell = (CGCell) entry.Value;
1040 cell.AppointmentTypeColor = (this.m_GridBackColor == "blue") ? Brushes.CornflowerBlue : Brushes.Khaki;
1041 }
1042 if ((this.m_pAvArray != null) && (this.m_pAvArray.Count != 0))
1043 {
1044 foreach (CGAvailability availability in this.m_pAvArray)
1045 {
1046 int nRow = 0;
1047 int nCol = 0;
1048 int num3 = 0;
1049 int num4 = 0;
1050 Brush brush = new SolidBrush(Color.FromArgb(availability.Red, availability.Green, availability.Blue));
1051 this.GetCellFromTime(availability.StartTime, ref nRow, ref nCol, true, availability.ResourceList);
1052 this.GetCellFromTime(availability.EndTime, ref num3, ref num4, false, availability.ResourceList);
1053 for (int i = nCol; i <= num4; i++)
1054 {
1055 for (int j = nRow; (i == num4) && (j <= num3); j++)
1056 {
1057 string str = "r" + j.ToString() + "c" + i.ToString();
1058 CGCell cell2 = (CGCell) this.m_gridCells.CellHashTable[str];
1059 if (cell2 != null)
1060 {
1061 cell2.AppointmentTypeColor = brush;
1062 }
1063 }
1064 }
1065 }
1066 }
1067 }
1068 }
1069
1070 private void SetColumnInfo()
1071 {
1072 this.m_ColumnInfoTable.Clear();
1073 for (int i = 0; i < this.m_sResourcesArray.Count; i++)
1074 {
1075 this.m_ColumnInfoTable.Add(this.m_sResourcesArray[i], i);
1076 }
1077 if (this.m_sResourcesArray.Count > 1)
1078 {
1079 this.m_nColumns = this.m_sResourcesArray.Count;
1080 }
1081 }
1082
1083 public void SetOverlapTable()
1084 {
1085 Hashtable hashtable = new Hashtable();
1086 int y = 0;
1087 int num2 = 0;
1088 int x = 0;
1089 foreach (CGAppointment appointment in this.m_Appointments.AppointmentTable.Values)
1090 {
1091 if (!appointment.WalkIn || this.m_bDrawWalkIns)
1092 {
1093 string resource = appointment.Resource;
1094 y = appointment.StartTime.Minute + (60 * appointment.StartTime.Hour);
1095 num2 = appointment.EndTime.Minute + (60 * appointment.EndTime.Hour);
1096 x = (this.m_sResourcesArray.Count > 1) ? (((int) this.m_ColumnInfoTable[resource]) + 1) : appointment.StartTime.DayOfYear;
1097 Rectangle rectangle = new Rectangle(x, y, 1, num2 - y);
1098 hashtable.Add(appointment.m_nKey, rectangle);
1099 }
1100 }
1101 this.m_ApptOverlapTable.Clear();
1102 foreach (int num4 in hashtable.Keys)
1103 {
1104 this.m_ApptOverlapTable.Add(num4, 0);
1105 }
1106 // Here it draws the Dates on Top
1107 if (this.m_ApptOverlapTable.Count != 0)
1108 {
1109 int num5 = (this.m_sResourcesArray.Count > 1) ? 1 : this.StartDate.DayOfYear;
1110 int num6 = (this.m_sResourcesArray.Count > 1) ? (this.m_sResourcesArray.Count + 1) : (this.Columns + this.StartDate.DayOfYear);
1111 for (int i = num5; i < num6; i++)
1112 {
1113 ArrayList list = new ArrayList();
1114 for (int j = 1; j < this.Rows; j++)
1115 {
1116 Rectangle rectangle2 = new Rectangle(i, j * this.m_nTimeScale, 1, this.m_nTimeScale);
1117 int num9 = -1;
1118 list.Clear();
1119 foreach (int num10 in hashtable.Keys)
1120 {
1121 Rectangle rect = (Rectangle) hashtable[num10];
1122 if (rectangle2.IntersectsWith(rect))
1123 {
1124 num9++;
1125 list.Add(num10);
1126 }
1127 }
1128 if (num9 > 0)
1129 {
1130 foreach (object obj2 in list)
1131 {
1132 int num11 = (int) obj2;
1133 if (((int) this.m_ApptOverlapTable[num11]) < num9)
1134 {
1135 this.m_ApptOverlapTable[num11] = num9;
1136 }
1137 }
1138 }
1139 }
1140 }
1141 }
1142 }
1143
1144 private void tickEventHandler(object o, EventArgs e)
1145 {
1146 Point point = new Point(base.AutoScrollPosition.X, base.AutoScrollPosition.Y);
1147 int x = point.X;
1148 int num = point.Y * -1;
1149 num = this.m_bScrollDown ? (num + 5) : (num - 5);
1150 point.Y = num;
1151 base.AutoScrollPosition = point;
1152 base.Invalidate();
1153 }
1154
1155 private bool TimesOverlap(DateTime dStart1, DateTime dEnd1, DateTime dStart2, DateTime dEnd2)
1156 {
1157 long ticks = dEnd1.Ticks - dStart1.Ticks;
1158 TimeSpan ts = new TimeSpan(ticks);
1159 ticks = dEnd2.Ticks - dStart2.Ticks;
1160 new TimeSpan(ticks).Subtract(ts);
1161 Rectangle rect = new Rectangle();
1162 Rectangle rectangle2 = new Rectangle();
1163 rect.X = 0;
1164 rectangle2.X = 0;
1165 rect.Width = 1;
1166 rectangle2.Width = 1;
1167 rect.Y = this.MinSince80(dStart1);
1168 rect.Height = this.MinSince80(dEnd1) - rect.Y;
1169 rectangle2.Y = this.MinSince80(dStart2);
1170 rectangle2.Height = this.MinSince80(dEnd2) - rectangle2.Y;
1171 return rectangle2.IntersectsWith(rect);
1172 }
1173
1174 /// <summary>
1175 /// The purpose of this is to properly draw the date boxes at the top of the calendar grid.
1176 /// Otherwise, when scrolling, it gets garbled.
1177 /// </summary>
1178 /// <param name="msg">Handles two messages:
1179 /// WM_VSCROLL (0x115 - Vertical Scrolling)
1180 /// WM_HSCROLL (0x114 - Horizontal Scrolling)
1181 /// </param>
1182 protected override void WndProc(ref Message msg)
1183 {
1184 try
1185 {
1186 if (msg.Msg == WM_VSCROLL)
1187 {
1188 this.m_bScroll = true;
1189 base.Invalidate(false);
1190 this.m_bScroll = false;
1191 }
1192 if (msg.Msg == WM_HSCROLL)
1193 {
1194 base.Invalidate(false);
1195 }
1196 base.WndProc(ref msg);
1197 }
1198 catch (Exception exception)
1199 {
1200 MessageBox.Show("CalendarGrid::WndProc: " + exception.Message + "\nStack: " + exception.StackTrace);
1201 }
1202 }
1203
1204 public CGAppointments Appointments
1205 {
1206 get
1207 {
1208 return this.m_Appointments;
1209 }
1210 set
1211 {
1212 this.m_Appointments = value;
1213 }
1214 }
1215
1216 public string ApptDragSource
1217 {
1218 get
1219 {
1220 return this.m_sDragSource;
1221 }
1222 set
1223 {
1224 this.m_sDragSource = value;
1225 }
1226 }
1227
1228 public ArrayList AvailabilityArray
1229 {
1230 get
1231 {
1232 return this.m_pAvArray;
1233 }
1234 set
1235 {
1236 this.m_pAvArray = value;
1237 }
1238 }
1239
1240 public int CellHeight
1241 {
1242 get
1243 {
1244 return this.m_cellHeight;
1245 }
1246 }
1247
1248 public ToolTip CGToolTip
1249 {
1250 get
1251 {
1252 return this.m_toolTip;
1253 }
1254 }
1255
1256 public int Columns
1257 {
1258 get
1259 {
1260 return this.m_nColumns;
1261 }
1262 set
1263 {
1264 if ((value > 0) && (value < 11))
1265 {
1266 this.m_nColumns = value;
1267 this.m_gridCells.ClearAllCells();
1268 this.m_selectedRange.Cells.ClearAllCells();
1269 Graphics g = base.CreateGraphics();
1270 this.BuildGridCellsArray(g);
1271 this.SetAppointmentTypes();
1272 base.Invalidate();
1273 }
1274 }
1275 }
1276
1277 public bool DrawWalkIns
1278 {
1279 get
1280 {
1281 return this.m_bDrawWalkIns;
1282 }
1283 set
1284 {
1285 this.m_bDrawWalkIns = value;
1286 }
1287 }
1288
1289 public string GridBackColor
1290 {
1291 get
1292 {
1293 return this.m_GridBackColor;
1294 }
1295 set
1296 {
1297 this.m_GridBackColor = value;
1298 }
1299 }
1300
1301 public bool GridEnter
1302 {
1303 get
1304 {
1305 return this.m_bGridEnter;
1306 }
1307 set
1308 {
1309 this.m_bGridEnter = value;
1310 }
1311 }
1312
1313 public ArrayList Resources
1314 {
1315 get
1316 {
1317 return this.m_sResourcesArray;
1318 }
1319 set
1320 {
1321 this.m_sResourcesArray = value;
1322 }
1323 }
1324
1325 public int Rows
1326 {
1327 get
1328 {
1329 return (0x5a0 / this.m_nTimeScale);
1330 }
1331 }
1332
1333 public int SelectedAppointment
1334 {
1335 get
1336 {
1337 return this.m_nSelectID;
1338 }
1339 set
1340 {
1341 this.m_nSelectID = value;
1342 }
1343 }
1344
1345 public CGAppointments SelectedAppointments
1346 {
1347 get
1348 {
1349 return this.m_SelectedAppointments;
1350 }
1351 }
1352
1353 public CGRange SelectedRange
1354 {
1355 get
1356 {
1357 return this.m_selectedRange;
1358 }
1359 }
1360
1361 public DateTime StartDate
1362 {
1363 get
1364 {
1365 return this.m_dtStart;
1366 }
1367 set
1368 {
1369 this.m_dtStart = value;
1370 }
1371 }
1372
1373 public int TimeScale
1374 {
1375 get
1376 {
1377 return this.m_nTimeScale;
1378 }
1379 set
1380 {
1381 if ((((value == 5) || (value == 10)) || ((value == 15) || (value == 20))) || ((value == 30) || (value == 60)))
1382 {
1383 this.m_nTimeScale = value;
1384 this.m_gridCells.ClearAllCells();
1385 this.m_selectedRange.Cells.ClearAllCells();
1386 Graphics g = base.CreateGraphics();
1387 this.BuildGridCellsArray(g);
1388 this.SetAppointmentTypes();
1389 base.Invalidate();
1390 }
1391 }
1392 }
1393
1394 }
1395}
1396
Note: See TracBrowser for help on using the repository browser.