private System.Windows.Rect GetRotatedRect(Roi roi)
 {
     System.Windows.Rect rotated;
     if (m_PersistentViewState.RotateTransform.Angle == 0)
     {
         rotated = roi.Rect;
     }
     else if (m_PersistentViewState.RotateTransform.Angle == 270)
     {
         rotated    = System.Windows.Rect.Transform(roi.Rect, new RotateTransform(90, 0, 0).Value);
         rotated.X += MaskBitmapSource.Width;
     }
     else if (m_PersistentViewState.RotateTransform.Angle == 180)
     {
         rotated    = System.Windows.Rect.Transform(roi.Rect, new RotateTransform(180, 0, 0).Value);
         rotated.X += MaskBitmapSource.Width;
         rotated.Y += MaskBitmapSource.Height;
     }
     else if (m_PersistentViewState.RotateTransform.Angle == 90)
     {
         rotated    = System.Windows.Rect.Transform(roi.Rect, new RotateTransform(270, 0, 0).Value);
         rotated.Y += MaskBitmapSource.Height;
     }
     else
     {
         throw new NotImplementedException(string.Format("Unsported Rect rotation: {}", m_PersistentViewState.RotateTransform.Angle.ToString()));
     }
     return(rotated);
 }
 public void ResizeBorderThicknessAccordingToGroupMembership(Roi roi, double scale)
 {
     if (m_SelectedRoisSubGroup1.Contains(roi))
     {
         ResizeBorderThicknessRoiAccordingToGroup(roi, m_SelectedRoisSubGroup1, scale);
     }
     else if (m_SelectedRoisSubGroup2.Contains(roi))
     {
         ResizeBorderThicknessRoiAccordingToGroup(roi, m_SelectedRoisSubGroup2, scale);
     }
     else if (m_SelectedRoisSubGroup3.Contains(roi))
     {
         ResizeBorderThicknessRoiAccordingToGroup(roi, m_SelectedRoisSubGroup3, scale);
     }
     else if (m_SelectedRois.Contains(roi))
     {
         ResizeBorderThicknessRoiAccordingToGroup(roi, m_SelectedRois, scale);
     }
     else if (m_GoldenRois.Contains(roi))
     {
         ResizeBorderThicknessRoiAccordingToGroup(roi, m_GoldenRois, scale);
     }
     else if (m_RecognitionRois.Contains(roi))
     {
         ResizeBorderThicknessRoiAccordingToGroup(roi, m_RecognitionRois, scale);
     }
     else if (m_Rois.Contains(roi))
     {
         ResizeBorderThicknessRoiAccordingToGroup(roi, m_Rois, scale);
     }
     else
     {
         throw new RoiNotMemeberOfAnyGroupException("Roi is not member of any group, and therefor can't be formatted.");
     }
 }
 private void SelectedRois_CollectionChanged(object sender, System.Collections.Specialized.NotifyCollectionChangedEventArgs e)
 {
     //removed rois
     if (e.Action == System.Collections.Specialized.NotifyCollectionChangedAction.Remove)
     {
         foreach (var oldRoi in e.OldItems)
         {
             Roi removedRoi = oldRoi as Roi;
             if (this.SelectedRoisSubGroup1.Contains(removedRoi))
             {
                 this.SelectedRoisSubGroup1.Remove(removedRoi);
             }
             if (this.SelectedRoisSubGroup2.Contains(removedRoi))
             {
                 this.SelectedRoisSubGroup2.Remove(removedRoi);
             }
             if (this.SelectedRoisSubGroup3.Contains(removedRoi))
             {
                 this.SelectedRoisSubGroup3.Remove(removedRoi);
             }
         }
     }
     else if (e.Action == System.Collections.Specialized.NotifyCollectionChangedAction.Add)
     {
         //do nothing
     }
     else if (e.Action == System.Collections.Specialized.NotifyCollectionChangedAction.Replace)
     {
         //TODO:
         throw new NotImplementedException();
     }
     else if (e.Action == System.Collections.Specialized.NotifyCollectionChangedAction.Move)
     {
         //TODO:
         throw new NotImplementedException();
     }
     else if (e.Action == System.Collections.Specialized.NotifyCollectionChangedAction.Reset)
     {
         //beware of redundant circular calls from child to parent clear. call the clear if the child sub collection was not cleared before.
         if (this.SelectedRoisSubGroup1.Count > 0)
         {
             this.SelectedRoisSubGroup1.Clear();
         }
         if (this.SelectedRoisSubGroup2.Count > 0)
         {
             this.SelectedRoisSubGroup2.Clear();
         }
         if (this.SelectedRoisSubGroup3.Count > 0)
         {
             this.SelectedRoisSubGroup3.Clear();
         }
     }
     else
     {
         //TODO:
         throw new NotImplementedException();
     }
     FormattableRoiCollectionChanged(e);
 }
        private void RedrawRoisOnMaskBitmapSource(Roi roi)
        {
            if (!m_MaskRedrawEnabled || roi.FillColor == Colors.Transparent) //saves 50% of the work - mask does not draw borders, only fill. Borders are drawn via Rectangles on a canvas.
            {
                return;
            }

            RedrawRoisOnMaskBitmapSource();
        }
 private void FormattableRoiCollectionChanged(System.Collections.Specialized.NotifyCollectionChangedEventArgs e)
 {
     //removed rois
     if (e.Action == System.Collections.Specialized.NotifyCollectionChangedAction.Remove)
     {
         foreach (var oldRoi in e.OldItems)
         {
             Roi removedRoi = oldRoi as Roi;
             FormatRoiAccordingToGroupMembership(removedRoi);
         }
     }
     else if (e.Action == System.Collections.Specialized.NotifyCollectionChangedAction.Add)
     {
         bool maskRedrawEnabled = m_MaskRedrawEnabled;
         //added rois
         foreach (var newRoi in e.NewItems)
         {
             Roi addedRoi = newRoi as Roi;
             FormatRoiAccordingToGroupMembership(addedRoi);
             if (maskRedrawEnabled)
             {
                 AddRoiToMaskBitmapSource(addedRoi);
             }
             m_MaskRedrawEnabled = false;         //Yoav 2013.05.21 after change of no auto redraw
             if (!this.m_Rois.Contains(addedRoi)) //Yoav 2013.05.20
             {
                 this.m_Rois.Add(addedRoi);
             }
             m_MaskRedrawEnabled = maskRedrawEnabled;
         }
     }
     else if (e.Action == System.Collections.Specialized.NotifyCollectionChangedAction.Replace)
     {
         //TODO:
         throw new NotImplementedException();
     }
     else if (e.Action == System.Collections.Specialized.NotifyCollectionChangedAction.Move)
     {
         //TODO:
         throw new NotImplementedException();
     }
     else if (e.Action == System.Collections.Specialized.NotifyCollectionChangedAction.Reset)
     {
         //assuming that all the Rois are also in the this.Rois collection, otherwise they will retain their original format.
         foreach (Roi roi in this.Rois)
         {
             FormatRoiAccordingToGroupMembership(roi);
         }
     }
     else
     {
         //TODO:
         throw new NotImplementedException();
     }
 }
        private void SelectedRoisSubGroup_CollectionChanged(object sender, System.Collections.Specialized.NotifyCollectionChangedEventArgs e)
        {
            //removed rois
            if (e.Action == System.Collections.Specialized.NotifyCollectionChangedAction.Remove)
            {
                foreach (var oldRoi in e.OldItems)
                {
                    Roi removedRoi = oldRoi as Roi;
                    if (this.SelectedRois.Contains(removedRoi))
                    {
                        this.SelectedRois.Remove(removedRoi);
                    }
                }
            }
            else if (e.Action == System.Collections.Specialized.NotifyCollectionChangedAction.Add)
            {
                //added rois
                foreach (var newRoi in e.NewItems)
                {
                    Roi addedRoi = newRoi as Roi;
                    if (!this.SelectedRois.Contains(addedRoi))
                    {
                        this.SelectedRois.Add(addedRoi);
                    }
                }
            }
            else if (e.Action == System.Collections.Specialized.NotifyCollectionChangedAction.Replace)
            {
                //TODO:
                throw new NotImplementedException();
            }
            else if (e.Action == System.Collections.Specialized.NotifyCollectionChangedAction.Move)
            {
                //TODO:
                throw new NotImplementedException();
            }
            else if (e.Action == System.Collections.Specialized.NotifyCollectionChangedAction.Reset)
            {
                //remove any ROI from selected parent group that does not belong in any of the 3 subgroups
                foreach (Roi roi in this.Rois)
                {
                    if (this.SelectedRois.Contains(roi) && !this.SelectedRoisSubGroup1.Contains(roi) && !this.SelectedRoisSubGroup2.Contains(roi) && !this.SelectedRoisSubGroup3.Contains(roi))
                    {
                        this.SelectedRois.Remove(roi);
                    }
                }
            }
            else
            {
                //TODO:
                throw new NotImplementedException();
            }

            FormattableRoiCollectionChanged(e);
        }
 /// <summary>
 /// This user control (Image Viewer) is listening to the changes in the ViewModel's ROI collection.
 /// When a ROI is added, or removed, the drawing canvas Rectangles (children) collection is updated, and the color of the last item is changed.
 /// </summary>
 /// <param name="sender"></param>
 /// <param name="e"></param>
 private void Rois_CollectionChanged(object sender, System.Collections.Specialized.NotifyCollectionChangedEventArgs e)
 {
     //removed rois
     if (e.Action == System.Collections.Specialized.NotifyCollectionChangedAction.Remove)
     {
         foreach (var oldRoi in e.OldItems)
         {
             Roi removedRoi = oldRoi as Roi;
             if (removedRoi.BorderColor != Colors.Transparent)
             {
                 if (this.drawingCanvas.Children.Contains(removedRoi.Rectangle))
                 {
                     this.drawingCanvas.Children.Remove(removedRoi.Rectangle);
                 }
             }
         }
     }
     else if (e.Action == System.Collections.Specialized.NotifyCollectionChangedAction.Add)
     {
         //added rois
         foreach (var newRoi in e.NewItems)
         {
             Roi addedRoi = newRoi as Roi;
             if (addedRoi.BorderColor != Colors.Transparent)
             {
                 if (!this.drawingCanvas.Children.Contains(addedRoi.Rectangle))
                 {
                     this.drawingCanvas.Children.Add(addedRoi.Rectangle);
                 }
             }
         }
         UpdateRectangleBorderThickness();
     }
     else if (e.Action == System.Collections.Specialized.NotifyCollectionChangedAction.Replace)
     {
         //TODO: in case ROI is last in list - need to change color
         throw new NotImplementedException();
     }
     else if (e.Action == System.Collections.Specialized.NotifyCollectionChangedAction.Move)
     {
         //TODO: in case ROI moved to be last in list - need to change color, and change the previous ROI which was last to default color
         throw new NotImplementedException();
     }
     else if (e.Action == System.Collections.Specialized.NotifyCollectionChangedAction.Reset)
     {
         this.drawingCanvas.Children.Clear();
     }
     else
     {
         //TODO:
         throw new NotImplementedException();
     }
 }
        private void RemoveRoi(Roi roi)
        {
            Roi removeRoi = m_PersistentViewState.RoisOriginalRects.Keys.FirstOrDefault <Roi>(r => r.LinkedObject.Equals(roi.LinkedObject));

            if (removeRoi == null)
            {
                throw new RoiNotExistsException("ROI does not exits, and therefor can't be removed.");
            }

            //m_Rois.Remove(removeRoi);
            m_PersistentViewState.RoisOriginalRects.Remove(removeRoi);
        }
 private void FormatRoiAccordingToGroup(Roi roi, RoiCollection collection)
 {
     roi.FillColor   = collection.FillColor;
     roi.BorderColor = collection.BorderColor;
     if (collection.CurrentUiBorderThickness > 0)
     {
         roi.BorderThickness = collection.CurrentUiBorderThickness;
     }
     else
     {
         roi.BorderThickness = collection.BorderThickness;
     }
 }
        /// <summary>
        /// When a ROI is added, the Rect property of the ROI is relative to the original non-transformed image (after skew of image and shift of ROI),
        /// so immediately after adding it, we must transform it to the current UI transformations state.
        /// If the ROI is added when no changes were applied via UI, there will be no change.
        /// </summary>
        /// <param name="roi"></param>
        private void AddRoi(Roi roi)
        {
            //m_Rois.Add(roi);
            //apply constant shift on every ROI which is added, currently seems that should never be used
            if (!m_PersistentViewState.Shift.IsEmpty)
            {
                roi.Rect = new System.Windows.Rect(m_PersistentViewState.Shift.X + roi.Rect.X, m_PersistentViewState.Shift.Y + roi.Rect.Y, +roi.Rect.Width, roi.Rect.Height);
            }
            m_PersistentViewState.RoisOriginalRects.Add(roi, roi.Rect);
            //TransformRoi(roi); //yoav 2013.05.16 un-necessary now

            //AddRoiToMaskBitmapSource(roi); //2013.05.19 removed - now will clear mask bitmap and redraw all ROIs on every change of any ROIs collection.
        }
        public void AddRoiToMaskBitmapSource(Roi roi)
        {
            DrawingVisual drawingVisual = new DrawingVisual();

            System.Windows.Rect rotated = GetRotatedRect(roi);

            using (DrawingContext drawingContext = drawingVisual.RenderOpen())
            {
                drawingContext.DrawRectangle(new SolidColorBrush(roi.FillColor), null, rotated);
                drawingContext.Close();
            }

            this.MaskBitmapSource.Render(drawingVisual);
        }
        private void FormatRoiAccordingToGroupMembership(Roi roi)
        {
            if (m_SelectedRoisSubGroup1.Contains(roi))
            {
                FormatRoiAccordingToGroup(roi, m_SelectedRoisSubGroup1);
            }
            else if (m_SelectedRoisSubGroup2.Contains(roi))
            {
                FormatRoiAccordingToGroup(roi, m_SelectedRoisSubGroup2);
            }
            else if (m_SelectedRoisSubGroup3.Contains(roi))
            {
                FormatRoiAccordingToGroup(roi, m_SelectedRoisSubGroup3);
            }
            else if (m_SelectedRois.Contains(roi))
            {
                FormatRoiAccordingToGroup(roi, m_SelectedRois);
            }
            else if (m_GoldenRois.Contains(roi))
            {
                FormatRoiAccordingToGroup(roi, m_GoldenRois);
            }
            else if (m_RecognitionRois.Contains(roi))
            {
                FormatRoiAccordingToGroup(roi, m_RecognitionRois);
            }
            else if (m_TableRois.Contains(roi))
            {
                FormatRoiAccordingToGroup(roi, m_TableRois);
            }
            else if (m_TableRegionRois.Contains(roi))
            {
                FormatRoiAccordingToGroup(roi, m_TableRegionRois);
            }
            else if (m_Rois.Contains(roi))
            {
                FormatRoiAccordingToGroup(roi, m_Rois);
            }
            else
            {
                throw new RoiNotMemeberOfAnyGroupException("Roi is not member of any group, and therefor can't be formatted.");
            }

            //RedrawRoisOnMaskBitmapSource(roi); //2013.05.19
        }
        //private void TransformRoi(Roi transRoi)
        //{
        //    transRoi.Rect = m_PersistentViewState.RoisOriginalRects[transRoi];
        //    transRoi.Rect.Transform(m_VolatileViewState.TransformGroup.Value); //doesn't work anyway
        //}

        private void Rois_CollectionChanged(object sender, System.Collections.Specialized.NotifyCollectionChangedEventArgs e)
        {
            //removed rois
            if (e.Action == System.Collections.Specialized.NotifyCollectionChangedAction.Remove)
            {
                foreach (var oldRoi in e.OldItems)
                {
                    Roi removedRoi = oldRoi as Roi;
                    this.RemoveRoi(removedRoi);
                }
                RedrawRoisOnMaskBitmapSource(); //since ROI could have been drawn over another ROI, just clearing the area under it is not enough.
            }
            else if (e.Action == System.Collections.Specialized.NotifyCollectionChangedAction.Add)
            {
                //added rois
                foreach (var newRoi in e.NewItems)
                {
                    Roi addedRoi = newRoi as Roi;
                    this.AddRoi(addedRoi);
                }
            }
            else if (e.Action == System.Collections.Specialized.NotifyCollectionChangedAction.Replace)
            {
                //TODO:
                throw new NotImplementedException();
            }
            else if (e.Action == System.Collections.Specialized.NotifyCollectionChangedAction.Move)
            {
                //TODO:
                throw new NotImplementedException();
            }
            else if (e.Action == System.Collections.Specialized.NotifyCollectionChangedAction.Reset)
            {
                m_PersistentViewState.RoisOriginalRects.Clear();
            }
            else
            {
                //TODO:
                throw new NotImplementedException();
            }

            FormattableRoiCollectionChanged(e);
        }
 private void ResizeBorderThicknessRoiAccordingToGroup(Roi roi, RoiCollection collection, double scale)
 {
     collection.CurrentUiBorderThickness = collection.BorderThickness / scale;
     roi.BorderThickness = collection.CurrentUiBorderThickness;
 }
 private void MoveRoi(Roi roi, int toPosition)
 {
     throw new NotImplementedException();
 }
 private void ReplaceRoi(Roi roi)
 {
     throw new NotImplementedException();
 }