private void RemoveSlotMachineGroupFromUI(SlotMachineGroupPair slotGroupPair)
        {
            SlotMachineGroup newMachineGroup = slotGroupPair.MachineGroup;
            DispatcherObject parent = LogicalTreeHelper.GetParent(newMachineGroup);

            if (slotGroupPair.IsAdded &&
                parent != null)
            {
                //if (!Monitor.TryEnter(_floorView._clearLock, 5))
                //{
                //    clearMachines = true;
                //    break;
                //}
                _canvas.Children.Remove(newMachineGroup);
                slotGroupPair.IsAdded = false;
            }
        }
        /// <summary>
        /// Refreshes the data.
        /// </summary>
        /// <param name="barPositions">The bar positions.</param>
        public void RefreshData(List<FloorStatusData> barPositions)
        {
            const string PROC = "[RefreshData]";
            double widthmargin = 10;
            double heightmargin = 20;
            var curPos = 1;
            bool clearMachines = false;
            bool groupby = false;
            _dispatcher.Invoke(new Action(
                   delegate()
                   {
                       groupby = _floorView.GroupByMachines;
                   }));
            bool hasPositionSaved = false;
            _floorView._teFloorPositions.Wait(TimeSpan.FromSeconds(30)); // wait for worst case seconds to retrive floor position from exchange server

            int userId = CDOSettings.Current.LoggedInUser.SecurityUserID;
            FloorPositionDto savedPositions = null;            

            try
            {
                // clear all the slot machine groupings
                if (_floorView.DisplayGroupMachines)
                {
                    foreach (var slotMachineGroupItem in _slotMachineGroups.Values)
                    {
                        slotMachineGroupItem.SlotMachineKeys.Clear();
                        if (!groupby)
                            _dispatcher.Invoke(new Action(
                                delegate()
                                {
                                    this.RemoveSlotMachineGroupFromUI(slotMachineGroupItem);
                                }));
                    }
                }

                // add or update the slot machines
                int rowIndex = 1;
                foreach (FloorStatusData position in barPositions)
                {
                    string key = position.Bar_Pos_Name;

                    _dispatcher.Invoke(new Action(
                        delegate()
                        {
                            SlotMachine newMachine = null;
                            SlotMachinePair pair = null;

                            if (_slotMachines.ContainsKey(key))
                            {
                                pair = _slotMachines[key];
                                newMachine = pair.Machine;
                            }
                            else
                            {
                                newMachine = new SlotMachine()
                                {
                                    SlotNumber = Convert.ToInt32(position.Bar_Pos_Name).ToString(),
                                    SlotNumberString = position.Bar_Pos_Name.ToString(),
                                    SlotID = position.Bar_Pos_No,
                                    AssetNumber = position.Asset_No
                                };
                                pair = new SlotMachinePair
                                {
                                    Key = key,
                                    PositionName = position.Bar_Pos_Name,
                                    AssetNo = position.Asset_No,
                                    Machine = newMachine
                                };
                                _slotMachines.Add(key, pair);
                            }

                            // slot status grouping
                            newMachine.SlotStatusString = position.Slot_Status;
                            SlotMachineGroupPair groupPair = null;
                            IList<string> groupItems = null;
                            if (_floorView.DisplayGroupMachines)
                            {
                                if (!_slotMachineGroups.ContainsKey(position.Slot_Status))
                                {
                                    groupPair = new SlotMachineGroupPair()
                                    {
                                        Status = _floorView.GetSlotStatus(position.Slot_Status),
                                        MachineGroup = new SlotMachineGroup()
                                        {
                                            Width = _canvas.Width - 10,
                                            Height = 30,
                                        },
                                        DisplayText = _floorView.GetSlotStatusDecription(position.Slot_Status),
                                    };
                                    _slotMachineGroups.Add(position.Slot_Status, groupPair);
                                }
                                else
                                {
                                    groupPair = _slotMachineGroups[position.Slot_Status];
                                }
                                groupItems = groupPair.SlotMachineKeys;
                                groupItems.Add(key);
                            }

                            // display game name instead of asset no
                            string assetNo = position.Asset_No;
                            if (Settings.DisplayGameNameInFloorView)
                            {
                                assetNo = position.Game_Name;
                            }

                            // Fix for Asset Number not displayed after finishing the Enrollment 
                            pair.AssetNo = assetNo;
                            newMachine.AssetNumber = assetNo;

                            pair.RowIndex = rowIndex++;
                            newMachine.Top = Convert.ToDouble(position.FLOORTOP);
                            newMachine.Left = Convert.ToDouble(position.FLOORLEFT);
                            _floorView.SetSlotMouseUpEvent(newMachine);

                            if (position.Install_No != 0)
                            {
                                newMachine.InstallationNo = position.Install_No;
                                newMachine.IsEventUnCleared = !(newMachine.IsEventUnCleared);
                                newMachine.IsEventUnCleared = (bool)position.UnClearedEvent;
                                newMachine.Status = (SlotMachineStatus)Enum.Parse(typeof(SlotMachineStatus), position.Slot_Status);
                                newMachine.StackerEventReceived = position.StackerEventReceived.HasValue ? position.StackerEventReceived.Value : false;
                                newMachine.IsCollectable = position.IsCollectable < 1;
                                if (newMachine.StackerEventReceived)
                                {
                                    newMachine.OuterRoundColor = Brushes.Goldenrod;
                                    newMachine.InnerRoundColor = Brushes.IndianRed;
                                }
                            }
                            else
                            {
                                newMachine.Status = SlotMachineStatus.EmptyPosition;
                                newMachine.InstallationNo = 0;
                            }
                            if (_floorView.DisplayGroupMachines &&
                                groupPair.MachineGroup.OuterColor == null)
                            {
                                groupPair.MachineGroup.OuterColor = _floorView._slotMachineGroupBgBrush;// newMachine.OuterRoundColor;
                                groupPair.MachineGroup.OuterForeColor = _floorView._slotMachineGroupFgBrush;// newMachine.ForeColorBrush;
                            }
                        }));
                }

                // remove the slot machine
                List<SlotMachinePair> removedMachines = (from a in _slotMachines
                                                         join b in barPositions
                                                         on a.Key equals b.Bar_Pos_Name
                                                         into matched
                                                         from c in matched.DefaultIfEmpty()
                                                         where c == null
                                                         select new SlotMachinePair
                                                         {
                                                             Key = a.Key,
                                                             Machine = a.Value.Machine
                                                         }).ToList();
                if (removedMachines != null)
                {
                    foreach (SlotMachinePair removedMachine in removedMachines)
                    {
                        _dispatcher.Invoke(new Action(
                        delegate()
                        {
                            this.ClearMachine(removedMachine.Machine);
                        }));
                        _slotMachines.Remove(removedMachine.Key);
                    }
                }

                // finally add the slot machines to the UI
                _dispatcher.Invoke(new Action(
                    delegate()
                    {
#if DEBUG
                        Stopwatch watch = new Stopwatch();
                        watch.Start();
#endif

                        try
                        {
                            if (groupby)
                            {
                                // draw the headers
                                int slotPerWidth = Convert.ToInt32((_floorView.Width - SlotMachine.SlotMachineGap) / SlotMachine.SlotMachineWidthGap);
                                int gap = SlotMachine.SlotMachineGap;
                                double y = gap;
                                foreach (var group in _slotMachineGroups)
                                {
                                    string title = group.Key;
                                    SlotMachineGroupPair groupPair = group.Value;
                                    SlotMachineGroup machineGroup = groupPair.MachineGroup;
                                    int slots = groupPair.SlotMachineKeys.Count;

                                    if (slots <= 0)
                                    {
                                        this.RemoveSlotMachineGroupFromUI(groupPair);
                                        continue;
                                    }
                                    this.AddSlotMachineGroupToUI(groupPair);

                                    groupPair.Left = 0;
                                    groupPair.Top = y;
                                    machineGroup.DisplayText = groupPair.DisplayText + " (" + slots.ToString() + ")";
                                    Canvas.SetLeft(machineGroup, groupPair.Left);
                                    Canvas.SetTop(machineGroup, groupPair.Top);
                                    _floorView.CalculateGroupedSlotMachines(groupPair, slotPerWidth);

                                    int row = 0;
                                    int column = 0;
                                    double sx = groupPair.Left + gap;
                                    double sy = groupPair.Top + machineGroup.Height + gap;
                                    foreach (var slotKey in groupPair.SlotMachineKeys)
                                    {
                                        SlotMachinePair slotPair = _slotMachines[slotKey];
                                        SlotMachine newMachine = slotPair.Machine;

                                        if (column >= slotPerWidth)
                                        {
                                            column = 0;
                                            row++;
                                            sx = groupPair.Left + gap;
                                            sy += SlotMachine.SlotMachineHeightGap;
                                        }

                                        Canvas.SetLeft(newMachine, sx);
                                        Canvas.SetTop(newMachine, sy);
                                        this.AddSlotMachineToUI(slotPair, newMachine);

                                        sx += SlotMachine.SlotMachineWidthGap;
                                        column++;
                                    }
                                    y += machineGroup.Height + groupPair.SlotsHeight + 5;
                                }

                                _canvas.Height = y + SlotMachine.SlotMachineGap;
                                _floorView.Border_Bottom.Margin = new Thickness(-50, 0, 0, 0);
                            }
                            else
                            {
                                List<string> orderedData = (from o in _slotMachines
                                                            orderby o.Value.RowIndex
                                                            select o.Key).ToList();
                                if (orderedData.Count > 72)
                                {
                                    _canvas.Height = (barPositions.Count / 12) * 110;
                                    _floorView.Border_Bottom.Width = 780;
                                    _floorView.Border_Bottom.Margin = new Thickness(-50, 0, 0, 0);
                                }

                                foreach (string slotKey in orderedData)
                                {
                                    SlotMachinePair slotPair = _slotMachines[slotKey];
                                    SlotMachine newMachine = slotPair.Machine;
                                    FloorPositionDataDto floorPosition = null;

                                    if (_floorView._floorViewUserLocations)
                                    {
                                        floorPosition = _floorView.GetFloorPosition(newMachine.SlotID);
                                        if (floorPosition != null)
                                        {
                                            newMachine.PositionData = floorPosition;
                                        }
                                    }

                                    UIElement dragging = _canvas.ElementBeingDragged;
                                    bool isDragging = false;
                                    if (dragging != null && dragging == newMachine)
                                    {
                                        isDragging = true;
                                    }

                                    if (!isDragging && _floorView._floorViewUserLocations)
                                    {
                                        if (floorPosition != null)
                                        {
                                            newMachine.Left = floorPosition.Left;
                                            newMachine.Top = floorPosition.Top;
                                            DragCanvas.SetZIndex(newMachine, floorPosition.RowNo);
                                        }
                                    }

                                    if (newMachine != null && !isDragging)
                                    {
                                        if (newMachine.Left > 0 || newMachine.Top > 0)
                                        {
                                            if ((_floorView.chkSortPos.IsChecked.Value) ||
                                                (_floorView.chkSortAsset.IsChecked.Value))
                                            {
                                                newMachine.Top = 0;
                                                newMachine.Left = 0;

                                                // Don't uncomment these lines, we should not reposition the slot machines during loading.
                                                // Slot machines position should be saved only during dragging.
                                                //if (newMachine.Status != SlotMachineStatus.EmptyPosition)
                                                //{
                                                //    _floorView.SaveFloorPosition(newMachine, true, ref hasPositionSaved);
                                                //}
                                                _floorView.CalculatePositionAndPaint(ref widthmargin, ref heightmargin, ref curPos, newMachine);
                                            }
                                            else
                                            {
                                                Canvas.SetLeft(newMachine, Convert.ToDouble(newMachine.Left));
                                                Canvas.SetTop(newMachine, Convert.ToDouble(newMachine.Top));
                                            }
                                        }
                                        else
                                        {
                                              _floorView.CalculatePositionAndPaint(ref widthmargin, ref heightmargin, ref curPos, newMachine);
                                              if (_floorView._floorViewUserLocations)
                                              {
                                                  if (!(_floorView.chkSortPos.IsChecked.Value &&
                                                        _floorView.chkSortAsset.IsChecked.Value))
                                                  {
                                                      if (savedPositions == null) savedPositions = new FloorPositionDto();
                                                      savedPositions.Modify(userId, newMachine.SlotID, TypeSystem.GetValueInt(newMachine.Left), TypeSystem.GetValueInt(newMachine.Top), 0);
                                                  }
                                              }
                                        }

                                        //// save the initial positions
                                        //if (CFloorView._FirstDragPosition)
                                        //{
                                        //    if (savedPositions == null) savedPositions = new FloorPositionDto();
                                        //    savedPositions.Modify(userId, newMachine.SlotID, TypeSystem.GetValueInt(newMachine.Left), TypeSystem.GetValueInt(newMachine.Top), 0);
                                        //}

                                        this.AddSlotMachineToUI(slotPair, newMachine);
                                    }
                                }
                            }
                        }
                        catch (ThreadAbortException)
                        {
                            LogManager.WriteLog(PROC + " => Thread was instructed to close.", LogManager.enumLogLevel.Error);
                        }
                        catch (Exception ex)
                        {
                            ExceptionManager.Publish(ex);
                        }
                        finally
                        {
#if DEBUG
                            watch.Stop();
                            LogManager.WriteLog(PROC + string.Format(" => Total time taken [{0}] to load the slot machines into UI.", watch.Elapsed.ToString()), LogManager.enumLogLevel.Info);
#endif
                            if (hasPositionSaved)
                            {
                                CDOSettings.Current.Save();
                            }

                            // notify the initial positions to all the clients logged in with the current user id
                            if (savedPositions != null && savedPositions.Count > 0)
                            {
                                _floorView.NotifyFloorPosition(savedPositions);                                
                            }
                            //if (CFloorView._FirstDragPosition)
                            //{
                            //    CFloorView._FirstDragPosition = false;
                            //}
                        }
                    }));

                if (clearMachines)
                {
                    LogManager.WriteLog(PROC + " => Unable to refresh. Clear machines called instead.", LogManager.enumLogLevel.Error);
                }
            }
            catch (ThreadAbortException)
            {
                LogManager.WriteLog(PROC + " => Thread was instructed to close.", LogManager.enumLogLevel.Error);
            }
            catch (Exception ex)
            {
                LogManager.WriteLog(PROC + " => Exception occured in function.", LogManager.enumLogLevel.Error);
                ExceptionManager.Publish(ex);
            }
            finally
            {
#if DEBUG
                LogManager.WriteLog(PROC + " => Finished.", LogManager.enumLogLevel.Error);
#endif
            }
        }
        private void AddSlotMachineGroupToUI(SlotMachineGroupPair slotGroupPair)
        {
            SlotMachineGroup newMachineGroup = slotGroupPair.MachineGroup;
            DispatcherObject parent = LogicalTreeHelper.GetParent(newMachineGroup);

            if (!slotGroupPair.IsAdded ||
                parent == null)
            {
                _canvas.Children.Add(newMachineGroup);
                slotGroupPair.IsAdded = true;
            }
        }
 internal void CalculateGroupedSlotMachines(SlotMachineGroupPair group, int slotPerWidth)
 {
     try
     {
         var slotLength = group.SlotMachineKeys.Count;
         int slotPerHeight = Convert.ToInt32(Math.Ceiling((double)(slotLength) / slotPerWidth));
         var ch = (slotPerHeight * SlotMachine.SlotMachineHeightGap) + SlotMachine.SlotMachineGap;
         group.SlotsHeight = ch;
     }
     catch { }
 }