프로젝트

일반

사용자정보

통계
| 브랜치(Branch): | 개정판:

markus / MarkupToPDF / Controls / Text / ArrowTextControl.cs @ 1170d58c

이력 | 보기 | 이력해설 | 다운로드 (78.3 KB)

1
using MarkupToPDF.Controls.Common;
2
using System;
3
using System.Collections.Generic;
4
using System.ComponentModel;
5
using System.Linq;
6
using System.Text;
7
using System.Threading.Tasks;
8
using System.Windows;
9
using System.Windows.Controls;
10
using System.Windows.Media;
11
using System.Windows.Shapes;
12
using MarkupToPDF.Controls.Custom;
13
using MarkupToPDF.Common;
14
using MarkupToPDF.Serialize.Core;
15
using MarkupToPDF.Serialize.S_Control;
16
using Markus.Fonts;
17

    
18
namespace MarkupToPDF.Controls.Text
19
{
20
    public class ArrowTextControl : CommentUserInfo, IDisposable, INotifyPropertyChanged, IPath, ITextControl, IMarkupControlData
21
    {
22
        private const string PART_ArrowPath = "PART_ArrowPath";
23
        private const string PART_TextBox = "PART_ArrowTextBox";
24
        //private const string PART_TextBlock = "PART_ArrowTextBlock";
25
        private const string PART_ArrowSubPath = "PART_ArrowSubPath";
26
        private const string PART_Border = "PART_Border";
27
        private const string PART_BaseTextbox_Caret = "Caret";
28

    
29
        public Path Base_ArrowPath = null;
30
        public Path Base_ArrowSubPath = null;
31
        public TextBox Base_TextBox = null;
32
        public TextBlock Base_TextBlock = null;
33
        public Border BaseTextbox_Caret = null;
34

    
35
        private const double _CloudArcDepth = 0.8;  /// 2018.05.14 added by humkyung
36

    
37
        #region Object & Variable
38
        GeometryGroup instanceGroup = new GeometryGroup();
39
        
40
        Path Cemy = new Path();
41
        LineGeometry connectorSMGeometry = new LineGeometry();
42
        LineGeometry connectorMEGeometry = new LineGeometry();
43

    
44
        public enum ArrowTextStyleSet { Normal, Cloud, Rect };
45

    
46
        #endregion
47

    
48
        static ArrowTextControl()
49
        {
50
            DefaultStyleKeyProperty.OverrideMetadata(typeof(ArrowTextControl), new FrameworkPropertyMetadata(typeof(ArrowTextControl)));
51
            //ResourceDictionary dictionary = new ResourceDictionary();
52
            //dictionary.Source = new Uri("/MarkupToPDF;component/themes/generic.xaml", UriKind.RelativeOrAbsolute);
53
            //if(!Application.Current.Resources.MergedDictionaries.Any(x=>x.Source == dictionary.Source))
54
            //    Application.Current.Resources.MergedDictionaries.Add(dictionary);
55
        }
56

    
57
        public ArrowTextControl()
58
        {
59
            //this.DefaultStyleKey = typeof(ArrowTextControl);
60
        }
61

    
62
        public override void OnApplyTemplate()
63
        {
64
            base.OnApplyTemplate();
65
            Base_ArrowPath = GetTemplateChild(PART_ArrowPath) as Path;
66
            Base_ArrowSubPath = GetTemplateChild(PART_ArrowSubPath) as Path;
67
            Base_TextBox = GetTemplateChild(PART_TextBox) as TextBox;
68
            BaseTextbox_Caret = GetTemplateChild(PART_BaseTextbox_Caret) as Border;
69
            Base_TextBox.Text = this.ArrowText;
70
           
71
            this.Base_TextBox.CaretIndex = this.Base_TextBox.Text.Length;
72
            this.Base_TextBox.CaretBrush = new SolidColorBrush(Colors.Transparent);
73
            this.Base_TextBox.ApplyTemplate();
74
            MoveCustomCaret();
75

    
76
            Base_TextBox.SizeChanged += new SizeChangedEventHandler(Base_TextBox_SizeChanged);
77
            Base_TextBox.GotFocus += new RoutedEventHandler(Base_TextBox_GotFocus);
78
            Base_TextBox.LostFocus += new RoutedEventHandler(Base_TextBox_LostFocus);
79
            Base_TextBox.SelectionChanged += (sender, e) => MoveCustomCaret();
80
            this.KeyDown += ArrowTextControl_KeyDown;
81
            SetArrowTextPath();
82
            Base_TextBox.IsTabStop = true;
83
        }
84

    
85
        private void ArrowTextControl_KeyDown(object sender, System.Windows.Input.KeyEventArgs e)
86
        {
87
           if(e.Key == System.Windows.Input.Key.Escape)
88
            {
89
                if(string.IsNullOrEmpty(Base_TextBox.Text))
90
                {
91
                    this.Visibility = Visibility.Collapsed;
92
                }
93

    
94
                EditEnd();
95
            }
96
        }
97

    
98
        public void SetFontFamily(FontFamily fontFamily)
99
        {
100
            this.FontFamily = fontFamily;
101
            this.TextFamily = fontFamily;
102
        }
103

    
104
        /// <summary>
105
        /// Moves the custom caret on the canvas.
106
        /// </summary>
107
        public void MoveCustomCaret()
108
        {
109
            var caretLocation = this.Base_TextBox.GetRectFromCharacterIndex(this.Base_TextBox.CaretIndex).Location;
110

    
111
            var angle = Math.Abs(this.PageAngle);
112
            //angle = 0;
113
            System.Diagnostics.Debug.WriteLine("Page Angle : " +  this.PageAngle);
114

    
115
            if (!double.IsInfinity(caretLocation.X))
116
            {
117
                if (angle == 90)
118
                {
119
                    Canvas.SetLeft(this.BaseTextbox_Caret, this.EndPoint.X + caretLocation.Y);
120
                }
121
                else if (angle == 180)
122
                {
123
                    
124
                    Canvas.SetLeft(this.BaseTextbox_Caret, (this.EndPoint.X+ this.Base_TextBox.ActualWidth) - caretLocation.X) ;
125
                    System.Diagnostics.Debug.WriteLine("Caret X : " + ((this.EndPoint.X + this.Base_TextBox.ActualWidth) - caretLocation.X));
126
                } 
127
                else if (angle == 270)
128
                {
129
                    Canvas.SetLeft(this.BaseTextbox_Caret, (this.EndPoint.X) - caretLocation.Y);
130
                }
131
                else
132
                {
133
                    System.Diagnostics.Debug.WriteLine("Caret X : " + (this.EndPoint.X - caretLocation.X));
134
                    Canvas.SetLeft(this.BaseTextbox_Caret, this.EndPoint.X + caretLocation.X);
135
                } 
136
            }
137

    
138
            if (!double.IsInfinity(caretLocation.Y))
139
            {
140
                if (angle == 90)
141
                {
142
                    Canvas.SetTop(this.BaseTextbox_Caret, this.EndPoint.Y - caretLocation.X);
143
                }
144
                else if (angle == 180)
145
                {//보정치40
146
                    Canvas.SetTop(this.BaseTextbox_Caret, ((this.EndPoint.Y -40) + this.Base_TextBox.ActualHeight)- caretLocation.Y );
147
                    System.Diagnostics.Debug.WriteLine("Caret Y : " + (((this.EndPoint.Y - 40) + this.Base_TextBox.ActualHeight) - caretLocation.Y));
148
                }
149
                else if (angle == 270)
150
                {
151
                    Canvas.SetTop(this.BaseTextbox_Caret, (this.EndPoint.Y) + caretLocation.X);
152
                }
153
                else
154
                {
155
                    Canvas.SetTop(this.BaseTextbox_Caret, this.EndPoint.Y  + caretLocation.Y);
156
                    System.Diagnostics.Debug.WriteLine("Caret Y : " + (this.EndPoint.Y + caretLocation.Y - BaseTextbox_Caret.ActualHeight));
157
                }
158
            }
159
        }
160

    
161
        public void MoveCustomCaret(Point point)
162
        {
163

    
164
            var caretLocation = this.Base_TextBox.GetRectFromCharacterIndex(this.Base_TextBox.CaretIndex).Location;
165

    
166
            if (!double.IsInfinity(caretLocation.X))
167
            {
168
                if (Math.Abs(this.PageAngle) == 90)
169
                {
170
                    Canvas.SetLeft(this.BaseTextbox_Caret, point.X + caretLocation.Y);
171
                }
172
                else if (Math.Abs(this.PageAngle) == 180)
173
                {
174

    
175
                    Canvas.SetLeft(this.BaseTextbox_Caret, (point.X + this.Base_TextBox.ActualWidth) - caretLocation.X);
176
                }
177
                else if (Math.Abs(this.PageAngle) == 270)
178
                {
179
                    Canvas.SetLeft(this.BaseTextbox_Caret, (point.X) - caretLocation.Y);
180
                }
181
                else
182
                {
183
                    Canvas.SetLeft(this.BaseTextbox_Caret, point.X + caretLocation.X);
184
                }
185
            }
186

    
187
            if (!double.IsInfinity(caretLocation.Y))
188
            {
189
                if (Math.Abs(this.PageAngle) == 90)
190
                {
191
                    Canvas.SetTop(this.BaseTextbox_Caret, point.Y - caretLocation.X);
192
                }
193
                else if (Math.Abs(this.PageAngle) == 180)
194
                {
195
                    Canvas.SetTop(this.BaseTextbox_Caret, (point.Y + this.Base_TextBox.ActualHeight) - caretLocation.Y);
196
                }
197
                else if (Math.Abs(this.CommentAngle) == 270)
198
                {
199
                    Canvas.SetTop(this.BaseTextbox_Caret, (point.Y) + caretLocation.X);
200
                }
201
                else
202
                {
203
                    Canvas.SetTop(this.BaseTextbox_Caret, point.Y + caretLocation.Y);
204
                }
205
            }
206
        }
207

    
208

    
209
        void Base_TextBox_LostFocus(object sender, RoutedEventArgs e)
210
        {
211
            EditEnd();
212
        }
213

    
214
        private void EditEnd()
215
        { 
216
            this.ArrowText = Base_TextBox.Text;
217
            Base_TextBox.Focusable = false;
218
            this.BaseTextbox_Caret.Visibility = Visibility.Collapsed;
219
            this.IsEditingMode = false;
220
            ApplyOverViewData();
221
        }
222

    
223
        void Base_TextBox_GotFocus(object sender, RoutedEventArgs e)
224
        {
225
            this.BaseTextbox_Caret.Visibility = Visibility.Visible;
226
            MoveCustomCaret();
227
            this.IsEditingMode = true;
228
        }
229

    
230
        void Base_TextBox_SizeChanged(object sender, SizeChangedEventArgs e)
231
        {
232
            if(this.IsEditingMode)
233
            {
234
                if (Base_TextBox.Text.Contains("|OR||DZ|"))
235
                {
236
                    Base_TextBox.Text = this.ArrowText;
237
                }
238

    
239
                this.ArrowText = Base_TextBox.Text;
240
                
241
            }
242
            BoxWidth = e.NewSize.Width;
243
            BoxHeight = e.NewSize.Height;
244
            SetArrowTextPath();
245
        }
246

    
247
        #region Properties
248
        private bool _IsEditingMode;
249
        public bool IsEditingMode
250
        {
251
            get
252
            {
253
                return _IsEditingMode;
254
            }
255
            set
256
            {
257
                _IsEditingMode = value;
258
                OnPropertyChanged("IsEditingMode");
259
            }
260
        }
261

    
262

    
263
        #endregion
264

    
265
        #region dp Properties
266
        //강인구 주석 풀기
267
        public Visibility TextBoxVisibility
268
        {
269
            get { return (Visibility)GetValue(TextBoxVisibilityProperty); }
270
            set
271
            {
272
                if (this.TextBoxVisibility != value)
273
                {
274
                    SetValue(TextBoxVisibilityProperty, value);
275
                    OnPropertyChanged("TextBoxVisibility");
276
                }
277
            }
278
        }
279

    
280
        //강인구 주석 풀기
281
        public Visibility TextBlockVisibility
282
        {
283
            get { return (Visibility)GetValue(TextBlockVisibilityProperty); }
284
            set
285
            {
286
                if (this.TextBlockVisibility != value)
287
                {
288
                    SetValue(TextBlockVisibilityProperty, value);
289
                    OnPropertyChanged("TextBlockVisibility");
290
                }
291
            }
292
        }
293

    
294

    
295
        public override SolidColorBrush StrokeColor
296
        {
297
            get { return (SolidColorBrush)GetValue(StrokeColorProperty); }
298
            set
299
            {
300
                if (this.StrokeColor != value)
301
                {
302
                    SetValue(StrokeColorProperty, value);
303
                }
304
            }
305
        }
306

    
307
        public PathGeometry SubPathData
308
        {
309
            get { return (PathGeometry)GetValue(SubPathDataProperty); }
310
            set
311
            {
312
                if (this.SubPathData != value)
313
                {
314
                    SetValue(SubPathDataProperty, value);
315
                }
316
            }
317
        }
318

    
319
        public string UserID
320
        {
321
            get { return (string)GetValue(UserIDProperty); }
322
            set
323
            {
324
                if (this.UserID != value)
325
                {
326
                    SetValue(UserIDProperty, value);
327
                    OnPropertyChanged("UserID");
328
                }
329
            }
330
        }
331

    
332
        public List<Point> PointSet
333
        {
334
            get { return (List<Point>)GetValue(PointSetProperty); }
335
            set { SetValue(PointSetProperty, value); }
336
        }
337

    
338
        public override bool IsSelected
339
        {
340
            get
341
            {
342
                return (bool)GetValue(IsSelectedProperty);
343
            }
344
            set
345
            {
346
                SetValue(IsSelectedProperty, value);
347
                OnPropertyChanged("IsSelected");
348
            }
349
        }
350

    
351
        public override ControlType ControlType
352
        {
353
            set
354
            {
355
                SetValue(ControlTypeProperty, value);
356
                OnPropertyChanged("ControlType");
357
            }
358
            get
359
            {
360
                return (ControlType)GetValue(ControlTypeProperty);
361
            }
362
        }
363

    
364
        public Point StartPoint
365
        {
366
            get { return (Point)GetValue(StartPointProperty); }
367
            set { SetValue(StartPointProperty, value); }
368
        }
369

    
370
        public Point EndPoint
371
        {
372
            get { return (Point)GetValue(EndPointProperty); }
373
            set { SetValue(EndPointProperty, value); }
374
        }
375

    
376
        public Point OverViewStartPoint
377
        {
378
            get { return (Point)GetValue(OverViewStartPointProperty); }
379
            set { SetValue(OverViewStartPointProperty, value); }
380
        }
381

    
382
        public Point OverViewEndPoint
383
        {
384
            get { return (Point)GetValue(OverViewEndPointProperty); }
385
            set { SetValue(OverViewEndPointProperty, value); }
386
        }
387

    
388

    
389
        //public double Angle
390
        //{
391
        //    get { return (double)GetValue(AngleProperty); }
392
        //    set { SetValue(AngleProperty, value); }
393
        //}
394

    
395
        public Thickness BorderSize
396
        {
397
            get { return (Thickness)GetValue(BorderSizeProperty); }
398
            set
399
            {
400
                if (this.BorderSize != value)
401
                {
402
                    SetValue(BorderSizeProperty, value);
403
                }
404
            }
405
        }
406

    
407

    
408
        public Point MidPoint
409
        {
410
            get { return (Point)GetValue(MidPointProperty); }
411
            set { SetValue(MidPointProperty, value); }
412
        }
413

    
414
        public bool isFixed
415
        {
416
            get { return (bool)GetValue(IsFixedProperty); }
417
            set { SetValue(IsFixedProperty, value); }
418
        }
419

    
420
        public bool isTrans
421
        {
422
            get { return (bool)GetValue(TransformerProperty); }
423
            set { SetValue(TransformerProperty, value); }
424
        }
425

    
426
        public bool isHighLight
427
        {
428
            get { return (bool)GetValue(isHighlightProperty); }
429
            set
430
            {
431
                if (this.isHighLight != value)
432
                {
433
                    SetValue(isHighlightProperty, value);
434
                    OnPropertyChanged("isHighLight");
435
                }
436
            }
437
        }
438

    
439
        public FontWeight TextWeight
440
        {
441
            get { return (FontWeight)GetValue(TextWeightProperty); }
442
            set
443
            {
444
                if (this.TextWeight != value)
445
                {
446
                    SetValue(TextWeightProperty, value);
447
                    OnPropertyChanged("TextWeight");
448
                }
449
            }
450
        }
451

    
452
        public Double LineSize
453
        {
454
            get { return (Double)GetValue(LineSizeProperty); }
455
            set
456
            {
457
                if (this.LineSize != value)
458
                {
459
                    SetValue(LineSizeProperty, value);
460
                }
461
            }
462
        }
463

    
464
        public Double BoxWidth
465
        {
466
            get { return (Double)GetValue(BoxWidthProperty); }
467
            set
468
            {
469
                if (this.BoxWidth != value)
470
                {
471
                    SetValue(BoxWidthProperty, value);
472
                }
473
            }
474
        }
475

    
476
        public Double BoxHeight
477
        {
478
            get { return (Double)GetValue(BoxHeightProperty); }
479
            set
480
            {
481
                if (this.BoxHeight != value)
482
                {
483
                    SetValue(BoxHeightProperty, value);
484
                }
485
            }
486
        }
487

    
488
        public ArrowTextStyleSet ArrowTextStyle
489
        {
490
            get { return (ArrowTextStyleSet)GetValue(ArrowTextStyleProperty); }
491
            set
492
            {
493
                if (this.ArrowTextStyle != value)
494
                {
495
                    SetValue(ArrowTextStyleProperty, value);
496
                }
497
            }
498
        }
499

    
500
        public Geometry PathData
501
        {
502
            get { return (Geometry)GetValue(PathDataProperty); }
503
            set { SetValue(PathDataProperty, value);
504

    
505
                OnPropertyChanged("PathData");
506
            }
507
        }
508

    
509
        public SolidColorBrush BackInnerColor
510
        {
511
            get { return (SolidColorBrush)GetValue(BackInnerColorProperty); }
512
            set
513
            {
514
                if (this.BackInnerColor != value)
515
                {
516
                    SetValue(BackInnerColorProperty, value);
517
                    OnPropertyChanged("BackInnerColor");
518
                }
519
            }
520
        }
521

    
522
        public Geometry PathDataInner
523
        {
524
            get { return (Geometry)GetValue(PathDataInnerProperty); }
525
            set
526
            {
527
                SetValue(PathDataInnerProperty, value);
528
                OnPropertyChanged("PathDataInner");
529
            }
530
        }
531

    
532
        public Geometry OverViewPathData
533
        {
534
            get { return (Geometry)GetValue(OverViewPathDataProperty); }
535
            set { SetValue(OverViewPathDataProperty, value);
536

    
537
                OnPropertyChanged("OverViewPathData");
538

    
539
            }
540
        }
541

    
542
        public FontFamily TextFamily
543
        {
544
            get { return (FontFamily)GetValue(TextFamilyProperty); }
545
            set
546
            {
547
                if (this.TextFamily != value)
548
                {
549
                    SetValue(TextFamilyProperty, value);
550
                    OnPropertyChanged("TextFamily");
551
                }
552
            }
553
        }
554

    
555
        public string ArrowText
556
        {
557
            get { return (string)GetValue(ArrowTextProperty); }
558
            set
559
            {
560
                if (this.ArrowText != value)
561
                {
562
                    SetValue(ArrowTextProperty, value);
563
                    OnPropertyChanged("ArrowText");
564
                }
565
            }
566
        }
567

    
568
        public string OverViewArrowText
569
        {
570

    
571
            get { return (string)GetValue(OverViewArrowTextProperty);
572
            }
573
            set
574
            {
575
                if (this.OverViewArrowText != value)
576
                {
577
                    SetValue(OverViewArrowTextProperty, value);
578
                    OnPropertyChanged("OverViewArrowText");
579
                }
580
            }
581
        }
582

    
583
        public Double TextSize
584
        {
585
            get { return (Double)GetValue(TextSizeProperty); }
586
            set
587
            {
588
                if (this.TextSize != value)
589
                {
590
                    SetValue(TextSizeProperty, value);
591
                    OnPropertyChanged("TextSize");
592
                }
593
            }
594
        }
595

    
596
        public FontStyle TextStyle
597
        {
598
            get { return (FontStyle)GetValue(TextStyleProperty); }
599
            set
600
            {
601
                if (this.TextStyle != value)
602
                {
603
                    SetValue(TextStyleProperty, value);
604
                    OnPropertyChanged("TextStyle");
605
                }
606
            }
607
        }
608

    
609
        //강인구 추가
610
        public TextDecorationCollection UnderLine
611
        {
612
            get
613
            {
614
                return (TextDecorationCollection)GetValue(UnderLineProperty);
615
            }
616
            set
617
            {
618
                if (this.UnderLine != value)
619
                {
620
                    SetValue(UnderLineProperty, value);
621
                    OnPropertyChanged("UnderLine");
622
                }
623
            }
624
        }
625

    
626
        public double CanvasX
627
        {
628
            get { return (double)GetValue(CanvasXProperty); }
629
            set
630
            {
631
                if (this.CanvasX != value)
632
                {
633
                    SetValue(CanvasXProperty, value);
634
                    OnPropertyChanged("CanvasX");
635
                }
636
            }
637
        }
638

    
639
        public double CanvasY
640
        {
641
            get { return (double)GetValue(CanvasYProperty); }
642
            set
643
            {
644
                if (this.CanvasY != value)
645
                {
646
                    SetValue(CanvasYProperty, value);
647
                    OnPropertyChanged("CanvasY");
648
                }
649
            }
650
        } 
651

    
652
        public double CenterX
653
        {
654
            get { return (double)GetValue(CenterXProperty); }
655
            set { SetValue(CenterXProperty, value);
656
            OnPropertyChanged("CenterX");
657
            
658
            }
659
        }
660

    
661
        public double CenterY
662
        {
663
            get { return (double)GetValue(CenterYProperty); }
664
            set { SetValue(CenterYProperty, value);
665
            OnPropertyChanged("CenterY");
666
            }
667
        }
668

    
669
        public Brush SubPathFill
670
        {
671
            get { return (Brush)GetValue(SubPathFillProperty); }
672
            set
673
            {
674
                SetValue(SubPathFillProperty, value);
675
                OnPropertyChanged("SubPathFill");
676
            }
677
        }
678

    
679
        public Brush TextBoxBackground
680
        {
681
            get { return (Brush)GetValue(TextBoxBackgroundProperty); }
682
            set
683
            {
684
                SetValue(TextBoxBackgroundProperty, value);
685
                OnPropertyChanged("TextBoxBackground");
686
            }
687
        }
688

    
689

    
690
        //강인구 추가 주석풀기
691
       
692

    
693
        public bool EnableEditing
694
        {
695
            get { return (bool)GetValue(EnableEditingProperty); }
696
            set
697
            {
698
                if (this.EnableEditing != value)
699
                {
700
                    SetValue(EnableEditingProperty, value);
701
                    OnPropertyChanged("EnableEditing");
702
                }
703
            }
704
        }
705

    
706
        #endregion
707

    
708
        #region Dependency Properties
709

    
710
        public static readonly DependencyProperty BoxWidthProperty = DependencyProperty.Register(
711
                "BoxWidth", typeof(double), typeof(ArrowTextControl), new PropertyMetadata((Double)20));
712

    
713
        public static readonly DependencyProperty BoxHeightProperty = DependencyProperty.Register(
714
                "BoxHeight", typeof(double), typeof(ArrowTextControl), new PropertyMetadata((Double)20));
715

    
716
        public static readonly DependencyProperty UserIDProperty = DependencyProperty.Register(
717
                "UserID", typeof(string), typeof(ArrowTextControl), new PropertyMetadata(null));
718

    
719
        public static readonly DependencyProperty ArrowTextStyleProperty = DependencyProperty.Register(
720
               "ArrowTextStyle", typeof(ArrowTextStyleSet), typeof(ArrowTextControl), new PropertyMetadata(ArrowTextStyleSet.Normal));
721

    
722
        public static readonly DependencyProperty CenterXProperty = DependencyProperty.Register(
723
                "CenterX", typeof(double), typeof(ArrowTextControl), new PropertyMetadata((double)0, OnCenterXYChanged));
724

    
725
        public static readonly DependencyProperty CenterYProperty = DependencyProperty.Register(
726
                "CenterY", typeof(double), typeof(ArrowTextControl), new PropertyMetadata((double)0, OnCenterXYChanged));
727

    
728
        public static readonly DependencyProperty AngleProperty = DependencyProperty.Register(
729
                "Angle", typeof(double), typeof(ArrowTextControl), new PropertyMetadata((double)0.0, new PropertyChangedCallback(PointValueChanged)));
730
        
731
        public static readonly DependencyProperty CanvasXProperty = DependencyProperty.Register(
732
                "CanvasX", typeof(double), typeof(ArrowTextControl), new PropertyMetadata((double)0, OnSetCansvasChanged));
733

    
734
        public static readonly DependencyProperty CanvasYProperty = DependencyProperty.Register(
735
                "CanvasY", typeof(double), typeof(ArrowTextControl), new PropertyMetadata((double)0, OnSetCansvasChanged));
736

    
737
        public static readonly DependencyProperty PointSetProperty = DependencyProperty.Register(
738
                "PointSet", typeof(List<Point>), typeof(ArrowTextControl), new PropertyMetadata(new List<Point>(), PointValueChanged));
739

    
740
        public static readonly DependencyProperty TextFamilyProperty = DependencyProperty.Register(
741
                "TextFamily", typeof(FontFamily), typeof(ArrowTextControl), new PropertyMetadata(new FontFamily("Arial"), TextChanged));
742

    
743
        public static readonly DependencyProperty PathDataProperty = DependencyProperty.Register(
744
                "PathData", typeof(Geometry), typeof(ArrowTextControl), null);
745

    
746
        //강인구 추가
747
        public static readonly DependencyProperty UnderLineProperty = DependencyProperty.Register(
748
    "UnderLine", typeof(TextDecorationCollection), typeof(ArrowTextControl), new PropertyMetadata(null, PointValueChanged));
749

    
750
        public static readonly DependencyProperty LineSizeProperty = DependencyProperty.Register(
751
               "LineSize", typeof(double), typeof(ArrowTextControl), new PropertyMetadata((Double)3, PointValueChanged));
752

    
753
        public static readonly DependencyProperty TextStyleProperty = DependencyProperty.Register(
754
                "TextStyle", typeof(FontStyle), typeof(ArrowTextControl), new PropertyMetadata(FontStyles.Normal));
755

    
756
        public static readonly DependencyProperty TextSizeProperty = DependencyProperty.Register(
757
                "TextSize", typeof(Double), typeof(ArrowTextControl), new PropertyMetadata((Double)30, PointValueChanged));
758

    
759
        public static readonly DependencyProperty TextWeightProperty = DependencyProperty.Register(
760
                "TextWeight", typeof(FontWeight), typeof(ArrowTextControl), new PropertyMetadata(FontWeights.Normal));
761

    
762
        public static readonly DependencyProperty IsFixedProperty = DependencyProperty.Register(
763
                "isFixed", typeof(bool), typeof(ArrowTextControl), new PropertyMetadata(false, PointValueChanged));
764

    
765
        public static readonly DependencyProperty IsSelectedProperty = DependencyProperty.Register(
766
                "IsSelected", typeof(bool), typeof(ArrowTextControl), new FrameworkPropertyMetadata(false, IsSelectedChanged));
767

    
768
        public static readonly DependencyProperty StrokeColorProperty = DependencyProperty.Register(
769
                "StrokeColor", typeof(SolidColorBrush), typeof(ArrowTextControl), new PropertyMetadata(new SolidColorBrush(Colors.Red)));
770

    
771
        public static readonly DependencyProperty ControlTypeProperty = DependencyProperty.Register(
772
                "ControlType", typeof(ControlType), typeof(ArrowTextControl), new FrameworkPropertyMetadata(ControlType.ArrowTextControl));
773

    
774
        public static readonly DependencyProperty StartPointProperty = DependencyProperty.Register(
775
                "StartPoint", typeof(Point), typeof(ArrowTextControl), new PropertyMetadata(new Point(0, 0), PointValueChanged));
776

    
777
        public static readonly DependencyProperty EndPointProperty = DependencyProperty.Register(
778
                "EndPoint", typeof(Point), typeof(ArrowTextControl), new PropertyMetadata(new Point(0, 0), PointValueChanged));
779

    
780
        public static readonly DependencyProperty BackInnerColorProperty = DependencyProperty.Register(
781
            "BackInnerColor", typeof(SolidColorBrush), typeof(ArrowTextControl), new PropertyMetadata(new SolidColorBrush(Colors.White)));
782

    
783
        public static readonly DependencyProperty PathDataInnerProperty = DependencyProperty.Register(
784
    "PathDataInner", typeof(Geometry), typeof(ArrowTextControl), null);
785

    
786
        public static readonly DependencyProperty isHighlightProperty = DependencyProperty.Register(
787
                "isHighlight", typeof(bool), typeof(ArrowTextControl), new PropertyMetadata(false, PointValueChanged));
788

    
789
        public static readonly DependencyProperty MidPointProperty = DependencyProperty.Register(
790
                "MidPoint", typeof(Point), typeof(ArrowTextControl), new PropertyMetadata(new Point(0, 0), PointValueChanged));
791

    
792
        public static readonly DependencyProperty TransformerProperty = DependencyProperty.Register(
793
                "isTrans", typeof(bool), typeof(ArrowTextControl), new PropertyMetadata(false, PointValueChanged));
794

    
795
        public static readonly DependencyProperty BorderSizeProperty = DependencyProperty.Register(
796
                "BorderSize", typeof(Thickness), typeof(ArrowTextControl), new PropertyMetadata(new Thickness(0), PointValueChanged));
797
    
798
        public static readonly DependencyProperty ArrowTextProperty = DependencyProperty.Register(
799
              "ArrowText", typeof(string), typeof(ArrowTextControl), new PropertyMetadata(null));
800

    
801

    
802

    
803
        //, new PropertyChangedCallback(TextChanged)
804

    
805

    
806
        #region 추가 사항
807
        public static readonly DependencyProperty SubPathDataProperty = DependencyProperty.Register(
808
                "SubPathData", typeof(Geometry), typeof(ArrowTextControl), null);
809

    
810

    
811
        public static readonly DependencyProperty SubPathFillProperty = DependencyProperty.Register(
812
                "SubPathFill", typeof(Brush), typeof(ArrowTextControl), new PropertyMetadata(null));
813

    
814
        public static readonly DependencyProperty TextBoxBackgroundProperty = DependencyProperty.Register(
815
                "TextBoxBackground", typeof(Brush), typeof(ArrowTextControl), new PropertyMetadata(Brushes.White));
816

    
817
        public static readonly DependencyProperty OverViewArrowTextProperty = DependencyProperty.Register(
818
                "OverViewArrowText", typeof(string), typeof(ArrowTextControl), new PropertyMetadata(null, new PropertyChangedCallback(TextChanged)));
819

    
820
        public static readonly DependencyProperty OverViewPathDataProperty = DependencyProperty.Register(
821
                "OverViewPathData", typeof(Geometry), typeof(ArrowTextControl), null);
822

    
823
        public static readonly DependencyProperty OverViewStartPointProperty = DependencyProperty.Register(
824
                "OverViewStartPoint", typeof(Point), typeof(ArrowTextControl), new PropertyMetadata(null));
825

    
826
        public static readonly DependencyProperty OverViewEndPointProperty = DependencyProperty.Register(
827
                "OverViewEndPoint", typeof(Point), typeof(ArrowTextControl), new PropertyMetadata(null));
828

    
829
        public static readonly DependencyProperty TextBoxVisibilityProperty = DependencyProperty.Register(
830
            "TextBoxVisibility", typeof(Visibility), typeof(ArrowTextControl), new PropertyMetadata((Visibility.Visible), OnTextBoxVisibilityChanged));
831

    
832
        //강인구 추가(주석풀기)
833
        public static readonly DependencyProperty TextBlockVisibilityProperty = DependencyProperty.Register(
834
            "TextBlockVisibility", typeof(Visibility), typeof(ArrowTextControl), new PropertyMetadata((Visibility.Collapsed), OnTextBlockVisibilityChanged));
835

    
836
        public static readonly DependencyProperty EnableEditingProperty = DependencyProperty.Register(
837
           "EnableEditing", typeof(bool), typeof(ArrowTextControl), new PropertyMetadata((true), new PropertyChangedCallback(OnIsEditingChanged)));
838

    
839
        #endregion
840

    
841
        #endregion
842

    
843
        #region CallBack Method
844

    
845
        //강인구 추가(주석풀기)
846
        public static void OnIsEditingChanged(DependencyObject sender, DependencyPropertyChangedEventArgs e)
847
        {
848
            var instance = (ArrowTextControl)sender;
849

    
850
            if (e.OldValue != e.NewValue && instance.Base_TextBlock != null)
851
            {
852
                instance.SetValue(e.Property, e.NewValue);
853

    
854
                if (instance.EnableEditing)
855
                {
856
                    instance.EditingMode();
857
                }
858
                else
859
                {
860
                    instance.UnEditingMode();
861
                }
862
            }
863
        }
864

    
865
        public static void OnTextBoxVisibilityChanged(DependencyObject sender, DependencyPropertyChangedEventArgs e)
866
        {
867
            var instance = (ArrowTextControl)sender;
868

    
869
            if (e.OldValue != e.NewValue && instance.Base_ArrowPath != null)
870
            {
871
                instance.SetValue(e.Property, e.NewValue);
872
            }
873
        }
874

    
875
        public static void OnTextBlockVisibilityChanged(DependencyObject sender, DependencyPropertyChangedEventArgs e)
876
        {
877
            var instance = (ArrowTextControl)sender;
878

    
879
            if (e.OldValue != e.NewValue && instance.Base_ArrowPath != null)
880
            {
881
                instance.SetValue(e.Property, e.NewValue);
882
            }
883
        }
884

    
885
        public static void PointValueChanged(DependencyObject sender, DependencyPropertyChangedEventArgs e)
886
        {
887
            var instance = (ArrowTextControl)sender;
888

    
889
            if (e.OldValue != e.NewValue && instance.Base_ArrowPath != null)
890
            {
891
                instance.SetArrowTextPath();
892
            }
893
        }
894

    
895

    
896

    
897
        public static void TextChanged(DependencyObject sender, DependencyPropertyChangedEventArgs e)
898
        {
899
            var instance = (ArrowTextControl)sender;
900
            
901
            if (e.OldValue != e.NewValue)
902
            {
903
                instance.SetValue(e.Property, e.NewValue);
904
                //instance.BoxWidth = instance.Base_TextBox.ActualWidth;
905
                //instance.BoxHeight = instance.Base_TextBox.ActualHeight;
906
            }
907
        }
908

    
909
        public static void OnCenterXYChanged(DependencyObject sender, DependencyPropertyChangedEventArgs e)
910
        {
911
            var instance = (ArrowTextControl)sender;
912
            if (e.OldValue != e.NewValue && instance.Base_ArrowPath != null)
913
            {
914
                instance.SetValue(e.Property, e.NewValue);
915
                instance.SetArrowTextPath();
916
            }
917
        }
918

    
919
        public static void OnSetCansvasChanged(DependencyObject sender, DependencyPropertyChangedEventArgs e)
920
        {
921
            var instance = (ArrowTextControl)sender;
922

    
923
            if (e.OldValue != e.NewValue && instance != null)
924
            {
925
                instance.SetValue(e.Property, e.NewValue);
926
                //Canvas.SetLeft(instance, instance.CanvasX);
927
                //Canvas.SetTop(instance, instance.CanvasY);
928
            }
929
        }
930

    
931
        public static void IsSelectedChanged(DependencyObject sender, DependencyPropertyChangedEventArgs e)
932
        {
933
            //var instance = (ArrowTextControl)sender;
934

    
935
            //if (e.OldValue != e.NewValue)
936
            //{
937
            //    instance.SetValue(e.Property, e.NewValue);
938

    
939
            //    if (instance.IsSelected && instance.Base_TextBox != null)
940
            //    {
941
            //        instance.BorderSize = new Thickness(1);
942
            //        //instance.Base_TextBox.BorderBrush = new SolidColorBrush(Colors.Blue);
943
            //        //instance.Base_ArrowPath.Stroke = new SolidColorBrush(Colors.Blue);
944
            //    }
945
            //    else
946
            //    {
947
            //        instance.BorderSize = new Thickness(0);
948
            //        //instance.Base_TextBox.BorderBrush = new SolidColorBrush(Colors.Transparent);
949
            //        //instance.Base_ArrowPath.Stroke = new SolidColorBrush(Colors.Transparent);
950
            //    }
951
            //}
952
        }
953
        #endregion
954

    
955
        #region Internal Method
956

    
957
        //강인구 주석 풀기
958
        public void EditingMode()
959
        {
960
            TextBoxVisibility = Visibility.Visible;
961
            TextBlockVisibility = Visibility.Collapsed;
962

    
963

    
964
            //강인구 언더라인 추가
965
            if (UnderLine != null)
966
                Base_TextBlock.TextDecorations = UnderLine;
967
        }
968
        //강인구 주석 풀기
969
        public void UnEditingMode()
970
        {
971

    
972
            TextBoxVisibility = Visibility.Collapsed;
973
            TextBlockVisibility = Visibility.Visible;
974

    
975
            if (UnderLine != null)
976
                Base_TextBlock.TextDecorations = UnderLine;
977

    
978
            Base_TextBlock.Margin =
979
                 new Thickness(Base_TextBox.Margin.Left + 4, Base_TextBox.Margin.Top + 4,
980
                     Base_TextBox.Margin.Right + 4, Base_TextBox.Margin.Bottom + 4);
981
        }
982

    
983
        private void SetArrowTextPath()
984
        {
985
            instanceGroup.Children.Clear();
986

    
987
            //VisualPageAngle = 0;
988

    
989
            if (Math.Abs(PageAngle).ToString() == "90")
990
            {
991
                VisualPageAngle = 270;
992
            }
993
            else if (Math.Abs(PageAngle).ToString() == "270")
994
            {
995
                VisualPageAngle = 90;
996
            }
997
            else
998
            {
999
                VisualPageAngle = PageAngle;
1000
            }
1001

    
1002
            connectorSMGeometry.StartPoint = this.StartPoint;
1003
            connectorSMGeometry.EndPoint = this.MidPoint;
1004
            connectorMEGeometry.StartPoint = this.MidPoint; //핵심
1005

    
1006
            /// 텍스트박스의 좌표 설정
1007
            Canvas.SetLeft(Base_TextBox, this.EndPoint.X);
1008
            Canvas.SetTop(Base_TextBox, this.EndPoint.Y);
1009
            //System.Diagnostics.Debug.WriteLine($"TextBox Set {this.EndPoint.X},{this.EndPoint.Y}");
1010
            
1011

    
1012
            List<Point> ps = new List<Point>();
1013
            ps.Add(new Point(Canvas.GetLeft(Base_TextBox) + this.BoxWidth / 2, Canvas.GetTop(Base_TextBox))); //상단
1014
            ps.Add(new Point(Canvas.GetLeft(Base_TextBox) + this.BoxWidth / 2, Canvas.GetTop(Base_TextBox) + this.BoxHeight)); // 하단
1015
            ps.Add(new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox) + this.BoxHeight / 2)); //좌단
1016
            ps.Add(new Point(Canvas.GetLeft(Base_TextBox) + this.BoxWidth, Canvas.GetTop(Base_TextBox) + this.BoxHeight / 2));  //우단
1017

    
1018
            if (isTrans)
1019
            {
1020
                switch (Math.Abs(this.PageAngle).ToString())
1021
                {
1022
                    case "90":
1023
                        {
1024
                            ps.Clear();
1025
                            ps.Add(new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox))); //위 왼쪽
1026
                            ps.Add(new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox) - this.BoxWidth / 2)); // 위 중간
1027
                            ps.Add(new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox) - this.BoxWidth)); // 위 오른쪽
1028

    
1029
                            ps.Add(new Point(Canvas.GetLeft(Base_TextBox) + this.BoxHeight / 2, Canvas.GetTop(Base_TextBox))); //왼쪽 중간
1030
                            ps.Add(new Point(Canvas.GetLeft(Base_TextBox) + this.BoxHeight, Canvas.GetTop(Base_TextBox))); //왼쪽 하단
1031

    
1032
                            ps.Add(new Point(Canvas.GetLeft(Base_TextBox) + this.BoxHeight, Canvas.GetTop(Base_TextBox) - this.BoxWidth / 2)); //중간 하단
1033
                            ps.Add(new Point(Canvas.GetLeft(Base_TextBox) + this.BoxHeight, Canvas.GetTop(Base_TextBox) - this.BoxWidth)); //오른쪽 하단
1034

    
1035
                            ps.Add(new Point(Canvas.GetLeft(Base_TextBox) + this.BoxHeight / 2, Canvas.GetTop(Base_TextBox) - this.BoxWidth)); //오른쪽 중간
1036
                        }
1037
                        break;
1038
                    case "270":
1039
                        {
1040
                            ps.Clear();
1041
                            ps.Add(new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox))); //위 왼쪽
1042
                            ps.Add(new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox) + this.BoxWidth / 2)); // 위 중간
1043
                            ps.Add(new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox) + this.BoxWidth)); // 위 오른쪽
1044

    
1045
                            ps.Add(new Point(Canvas.GetLeft(Base_TextBox) - this.BoxHeight / 2, Canvas.GetTop(Base_TextBox))); //왼쪽 중간
1046
                            ps.Add(new Point(Canvas.GetLeft(Base_TextBox) - this.BoxHeight, Canvas.GetTop(Base_TextBox))); //왼쪽 하단
1047

    
1048
                            ps.Add(new Point(Canvas.GetLeft(Base_TextBox) - this.BoxHeight, Canvas.GetTop(Base_TextBox) + this.BoxWidth / 2)); //중간 하단
1049
                            ps.Add(new Point(Canvas.GetLeft(Base_TextBox) - this.BoxHeight, Canvas.GetTop(Base_TextBox) + this.BoxWidth)); //오른쪽 하단
1050

    
1051
                            ps.Add(new Point(Canvas.GetLeft(Base_TextBox) - this.BoxHeight / 2, Canvas.GetTop(Base_TextBox) + this.BoxWidth)); //오른쪽 중간
1052
                        }
1053
                        break;
1054
                    default:
1055
                        break;
1056
                }
1057
                
1058
                var endP = MathSet.getNearPoint(ps, this.MidPoint);
1059

    
1060
                //20180911 LJY 꺾이는 부분 수정
1061
                Point testP = endP;                
1062
                switch (Math.Abs(this.PageAngle).ToString())
1063
                {
1064
                    case "90":
1065
                        testP = new Point(endP.X + 50, endP.Y);
1066
                        break;
1067
                    case "270":
1068
                        testP = new Point(endP.X - 50, endP.Y);
1069
                        break;
1070
                }                
1071

    
1072
                //20180910 LJY 각도에 따라.
1073
                switch (Math.Abs(this.PageAngle).ToString())
1074
                {
1075
                    case "90":
1076
                        if (isFixed)
1077
                        {
1078
                            if (ps[0] == endP) //상단
1079
                            {
1080
                                testP = new Point(endP.X , endP.Y + 50);
1081
                                //System.Diagnostics.Debug.WriteLine("상단"+ testP);
1082
                            }
1083
                            else if (ps[1] == endP) //하단
1084
                            {
1085
                                testP = new Point(endP.X , endP.Y - 50);
1086
                                //System.Diagnostics.Debug.WriteLine("하단"+ testP);
1087
                            }
1088
                            else if (ps[2] == endP) //좌단
1089
                            {
1090
                                testP = new Point(endP.X - 50, endP.Y);
1091
                                //System.Diagnostics.Debug.WriteLine("좌단"+ testP);
1092
                            }
1093
                            else if (ps[3] == endP) //우단
1094
                            {
1095
                                testP = new Point(endP.X + 50, endP.Y);
1096
                                //System.Diagnostics.Debug.WriteLine("우단"+ testP);
1097
                            }
1098
                        }
1099
                        break;
1100
                    case "270":
1101
                        if (isFixed)
1102
                        {
1103
                            if (ps[0] == endP) //상단
1104
                            {
1105
                                testP = new Point(endP.X , endP.Y - 50);
1106
                                //System.Diagnostics.Debug.WriteLine("상단" + testP);
1107
                            }
1108
                            else if (ps[1] == endP) //하단
1109
                            {
1110
                                testP = new Point(endP.X, endP.Y + 50);
1111
                                //System.Diagnostics.Debug.WriteLine("하단" + testP);
1112
                            }
1113
                            else if (ps[2] == endP) //좌단
1114
                            {
1115
                                testP = new Point(endP.X + 50, endP.Y);
1116
                                //System.Diagnostics.Debug.WriteLine("좌단" + testP);
1117
                            }
1118
                            else if (ps[3] == endP) //우단
1119
                            {
1120
                                testP = new Point(endP.X - 50, endP.Y);
1121
                                //System.Diagnostics.Debug.WriteLine("우단" + testP);
1122
                            }
1123
                        }
1124
                        break;
1125
                    default:
1126
                        if (isFixed)
1127
                        {
1128
                            if (ps[0] == endP) //상단
1129
                            {
1130
                                testP = new Point(endP.X, endP.Y - 50);
1131
                                //System.Diagnostics.Debug.WriteLine("상단");
1132
                            }
1133
                            else if (ps[1] == endP) //하단
1134
                            {
1135
                                testP = new Point(endP.X, endP.Y + 50);
1136
                                //System.Diagnostics.Debug.WriteLine("하단");
1137
                            }
1138
                            else if (ps[2] == endP) //좌단
1139
                            {
1140
                                testP = new Point(endP.X - 50, endP.Y);
1141
                                //System.Diagnostics.Debug.WriteLine("좌단");
1142
                            }
1143
                            else if (ps[3] == endP) //우단
1144
                            {
1145
                                testP = new Point(endP.X + 50, endP.Y);
1146
                                //System.Diagnostics.Debug.WriteLine("우단");
1147
                            }
1148
                        }
1149
                        break;
1150
                }
1151
                connectorMEGeometry.EndPoint = endP;
1152
                connectorSMGeometry.EndPoint = testP;
1153
                connectorMEGeometry.StartPoint = testP;
1154
                
1155
                //20180910 LJY 각도에 따라.
1156
                this.MidPoint = testP;
1157
                instanceGroup.Children.Add(DrawSet.DrawArrow(testP, this.StartPoint, this.LineSize));
1158
                instanceGroup.FillRule = FillRule.Nonzero;
1159
                this.Base_ArrowPath.Fill = this.StrokeColor;
1160
                this.Base_ArrowSubPath.Fill = this.StrokeColor;
1161
            }
1162
            else
1163
            {
1164
                switch (Math.Abs(this.PageAngle).ToString())
1165
                {
1166
                    case "90":
1167
                        {
1168
                            ps.Clear();
1169

    
1170
                            ps.Add(new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox))); //위 왼쪽
1171
                            ps.Add(new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox) - this.BoxWidth / 2)); // 위 중간
1172
                            ps.Add(new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox) - this.BoxWidth)); // 위 오른쪽
1173

    
1174
                            ps.Add(new Point(Canvas.GetLeft(Base_TextBox) + this.BoxHeight / 2, Canvas.GetTop(Base_TextBox))); //왼쪽 중간
1175
                            ps.Add(new Point(Canvas.GetLeft(Base_TextBox) + this.BoxHeight, Canvas.GetTop(Base_TextBox))); //왼쪽 하단
1176

    
1177
                            ps.Add(new Point(Canvas.GetLeft(Base_TextBox) + this.BoxHeight, Canvas.GetTop(Base_TextBox) - this.BoxWidth / 2)); //중간 하단
1178
                            ps.Add(new Point(Canvas.GetLeft(Base_TextBox) + this.BoxHeight, Canvas.GetTop(Base_TextBox) - this.BoxWidth)); //오른쪽 하단
1179
                            ps.Add(new Point(Canvas.GetLeft(Base_TextBox) + this.BoxHeight / 2, Canvas.GetTop(Base_TextBox) - this.BoxWidth)); //오른쪽 중간 
1180
                        }
1181
                        break;
1182
                    case "270":
1183
                        {
1184
                            ps.Clear();
1185
                            
1186
                            ps.Add(new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox))); //위 왼쪽
1187
                            ps.Add(new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox) + this.BoxWidth / 2)); // 위 중간
1188
                            ps.Add(new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox) + this.BoxWidth)); // 위 오른쪽
1189

    
1190
                            ps.Add(new Point(Canvas.GetLeft(Base_TextBox) - this.BoxHeight / 2, Canvas.GetTop(Base_TextBox))); //왼쪽 중간
1191
                            ps.Add(new Point(Canvas.GetLeft(Base_TextBox) - this.BoxHeight, Canvas.GetTop(Base_TextBox))); //왼쪽 하단
1192

    
1193
                            ps.Add(new Point(Canvas.GetLeft(Base_TextBox) - this.BoxHeight, Canvas.GetTop(Base_TextBox) + this.BoxWidth / 2)); //중간 하단
1194
                            ps.Add(new Point(Canvas.GetLeft(Base_TextBox) - this.BoxHeight, Canvas.GetTop(Base_TextBox) + this.BoxWidth)); //오른쪽 하단
1195

    
1196
                            ps.Add(new Point(Canvas.GetLeft(Base_TextBox) - this.BoxHeight / 2, Canvas.GetTop(Base_TextBox) + this.BoxWidth)); //오른쪽 중간 
1197
                        }
1198
                        break;
1199
                    //case "180":
1200
                    //    {
1201
                    //        ps.Clear();
1202

    
1203
                    //        ps.Add(new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox))); //위 왼쪽
1204
                    //        ps.Add(new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox) + this.BoxWidth / 2)); // 위 중간
1205
                    //        ps.Add(new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox) + this.BoxWidth)); // 위 오른쪽
1206

    
1207
                    //        ps.Add(new Point(Canvas.GetLeft(Base_TextBox) + this.BoxHeight / 2, Canvas.GetTop(Base_TextBox))); //왼쪽 중간
1208
                    //        ps.Add(new Point(Canvas.GetLeft(Base_TextBox) + this.BoxHeight, Canvas.GetTop(Base_TextBox))); //왼쪽 하단
1209

    
1210
                    //        ps.Add(new Point(Canvas.GetLeft(Base_TextBox) + this.BoxHeight, Canvas.GetTop(Base_TextBox) + this.BoxWidth / 2)); //중간 하단
1211
                    //        ps.Add(new Point(Canvas.GetLeft(Base_TextBox) + this.BoxHeight, Canvas.GetTop(Base_TextBox) + this.BoxWidth)); //오른쪽 하단
1212

    
1213
                    //        ps.Add(new Point(Canvas.GetLeft(Base_TextBox) + this.BoxHeight / 2, Canvas.GetTop(Base_TextBox) + this.BoxWidth)); //오른쪽 중간 
1214
                    //    }
1215
                    //    break;
1216
                    default:
1217
                        break;
1218
                }
1219

    
1220

    
1221
                var endP = MathSet.getNearPoint(ps, this.MidPoint);
1222
                connectorMEGeometry.EndPoint = endP; //최상단
1223
                                                     //connectorMEGeometry.EndPoint = this.EndPoint; //핵심
1224
                                                     //this.MidPoint= MathSet.getMiddlePoint(this.StartPoint, endP);
1225
                #region 보정치
1226
                Point testP = endP;
1227

    
1228
                //20180910 LJY 각도에 따라.
1229
                switch (Math.Abs(this.PageAngle).ToString())
1230
                {
1231
                    case "90":
1232
                        if (isFixed)
1233
                        {
1234
                            if (ps[0] == endP) //상단
1235
                            {
1236
                                testP = new Point(endP.X - 50, endP.Y);
1237
                                //System.Diagnostics.Debug.WriteLine("상단"+ testP);
1238
                            }
1239
                            else if (ps[1] == endP) //하단
1240
                            {
1241
                                testP = new Point(endP.X + 50, endP.Y);
1242
                                //System.Diagnostics.Debug.WriteLine("하단"+ testP);
1243
                            }
1244
                            else if (ps[2] == endP) //좌단
1245
                            {
1246
                                testP = new Point(endP.X - 50, endP.Y);
1247
                                //System.Diagnostics.Debug.WriteLine("좌단"+ testP);
1248
                            }
1249
                            else if (ps[3] == endP) //우단
1250
                            {
1251
                                testP = new Point(endP.X + 50 , endP.Y);
1252
                                //System.Diagnostics.Debug.WriteLine("우단"+ testP);
1253
                            }
1254
                        }
1255
                        break;
1256
                    case "270":
1257
                        if (isFixed)
1258
                        {
1259
                            if (ps[0] == endP) //상단
1260
                            {
1261
                                testP = new Point(endP.X + 50, endP.Y);
1262
                                //System.Diagnostics.Debug.WriteLine("상단" + testP);
1263
                            }
1264
                            else if (ps[1] == endP) //하단
1265
                            {
1266
                                testP = new Point(endP.X - 50, endP.Y);
1267
                                //System.Diagnostics.Debug.WriteLine("하단" + testP);
1268
                            }
1269
                            else if (ps[2] == endP) //좌단
1270
                            {
1271
                                testP = new Point(endP.X + 50, endP.Y);
1272
                                //System.Diagnostics.Debug.WriteLine("좌단" + testP);
1273
                            }
1274
                            else if (ps[3] == endP) //우단
1275
                            {
1276
                                testP = new Point(endP.X + 50, endP.Y );
1277
                                //System.Diagnostics.Debug.WriteLine("우단" + testP);
1278
                            }
1279
                        }
1280
                        break;
1281
                    default:
1282
                        if (isFixed)
1283
                        {
1284
                            if (ps[0] == endP) //상단
1285
                            {
1286
                                testP = new Point(endP.X, endP.Y - 50);
1287
                                //System.Diagnostics.Debug.WriteLine("상단");
1288
                            }
1289
                            else if (ps[1] == endP) //하단
1290
                            {
1291
                                testP = new Point(endP.X, endP.Y + 50);
1292
                                //System.Diagnostics.Debug.WriteLine("하단");
1293
                            }
1294
                            else if (ps[2] == endP) //좌단
1295
                            {
1296
                                testP = new Point(endP.X - 50, endP.Y);
1297
                                //System.Diagnostics.Debug.WriteLine("좌단");
1298
                            }
1299
                            else if (ps[3] == endP) //우단
1300
                            {
1301
                                testP = new Point(endP.X + 50, endP.Y);
1302
                                //System.Diagnostics.Debug.WriteLine("우단");
1303
                            }
1304
                        }
1305
                        break;
1306
                }
1307
                  
1308

    
1309
                connectorSMGeometry.EndPoint = testP;
1310
                connectorMEGeometry.StartPoint = testP;
1311
                instanceGroup.Children.Add(DrawSet.DrawArrow(testP, this.StartPoint, this.LineSize));
1312
                instanceGroup.FillRule = FillRule.Nonzero;
1313
                this.Base_ArrowPath.Fill = this.StrokeColor;
1314
                this.Base_ArrowSubPath.Fill = this.StrokeColor;
1315
                #endregion
1316
            }
1317

    
1318
            switch (this.ArrowTextStyle)
1319
            {
1320
                case ArrowTextStyleSet.Normal:
1321
                    this.BorderSize = new Thickness(0);
1322
                    DrawingRect();
1323
                    break;
1324
                case ArrowTextStyleSet.Cloud:
1325
                    this.BorderSize = new Thickness(0);
1326
                    DrawingCloud();
1327
                    break;
1328
                default:
1329
                    {
1330
                        this.BorderSize = new Thickness(LineSize); //올라
1331
                        DrawingRect();
1332
                    }
1333

    
1334
                    break;
1335
            }
1336

    
1337
            if (isHighLight)
1338
            {
1339
                SubPathFill = new SolidColorBrush(Color.FromArgb(Convert.ToByte(255 * 0.6), Colors.Yellow.R, Colors.Yellow.G, Colors.Yellow.B));
1340
                BackInnerColor = new SolidColorBrush(Color.FromArgb(Convert.ToByte(255 * 0.6), Colors.Yellow.R, Colors.Yellow.G, Colors.Yellow.B));
1341

    
1342
                TextBoxBackground = new SolidColorBrush(Color.FromArgb(Convert.ToByte(255 * 0.6), Colors.Yellow.R, Colors.Yellow.G, Colors.Yellow.B));
1343
            }
1344
            else
1345
            {
1346
                BackInnerColor = new SolidColorBrush(Color.FromArgb(Convert.ToByte(255 * 0.6), Colors.White.R, Colors.White.G, Colors.White.B));
1347
                SubPathFill = new SolidColorBrush(Color.FromArgb(Convert.ToByte(255 * 0.6), Colors.White.R, Colors.White.G, Colors.White.B));
1348
                TextBoxBackground = new SolidColorBrush(Color.FromArgb(Convert.ToByte(255 * 0.1), Colors.White.R, Colors.White.G, Colors.White.B));
1349
            }
1350

    
1351
            instanceGroup.Children.Add(connectorSMGeometry);
1352
            instanceGroup.Children.Add(connectorMEGeometry);
1353

    
1354
            this.PathData = instanceGroup;
1355
            OverViewPathData = PathData;
1356
            OverViewArrowText = ArrowText;
1357
            OverViewEndPoint = connectorMEGeometry.EndPoint;
1358
            OverViewStartPoint = connectorSMGeometry.StartPoint;
1359

    
1360
            var tempAngle = Math.Abs(this.PageAngle);
1361

    
1362
            if (tempAngle == Convert.ToDouble(90) || tempAngle == Convert.ToDouble(270))
1363
            {
1364
                this.RenderTransformOrigin = new Point(0.5, 0.5);
1365
                this.Base_ArrowPath.RenderTransformOrigin = new Point(0, 0);
1366
                this.Base_ArrowSubPath.RenderTransformOrigin = new Point(0, 0);
1367

    
1368
                Base_TextBox.RenderTransformOrigin = new Point(0, 0);
1369
                BaseTextbox_Caret.RenderTransformOrigin = new Point(0, 0);
1370
            }
1371

    
1372
            Base_TextBox.RenderTransform = new RotateTransform
1373
            {
1374
                Angle = this.VisualPageAngle,
1375
                CenterX = this.CenterX,
1376
                CenterY = this.CenterY,
1377
            };
1378

    
1379
            System.Diagnostics.Debug.WriteLine($"base TextBox center X : {this.CenterX} Y : {this.CenterY} ");
1380

    
1381
            
1382

    
1383
            Base_ArrowSubPath.RenderTransform = new RotateTransform
1384
            {
1385
                Angle = this.VisualPageAngle,
1386
                CenterX = this.EndPoint.X,
1387
                CenterY = this.EndPoint.Y,
1388
            };
1389

    
1390
            if (BaseTextbox_Caret.Visibility == Visibility.Visible)
1391
            {
1392
                BaseTextbox_Caret.RenderTransform = new RotateTransform
1393
                {
1394
                    Angle = this.VisualPageAngle,
1395
                    CenterX = this.CenterX,
1396
                    CenterY = this.CenterY,
1397
                };
1398

    
1399
                MoveCustomCaret();
1400
            }
1401
        }
1402

    
1403
        private void DrawingCloud()
1404
        {
1405
            //20180906 LJY Textbox guide
1406
            string angle = Math.Abs(this.PageAngle).ToString();
1407
            if (angle == "180")
1408
            {
1409
                List<Point> pCloud = new List<Point>()
1410
                {
1411
                     new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox)), //위
1412
                    new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox) - BoxHeight), //왼쪽 아래
1413
                    new Point(Canvas.GetLeft(Base_TextBox) - BoxWidth, Canvas.GetTop(Base_TextBox) - BoxHeight),
1414
                    new Point(Canvas.GetLeft(Base_TextBox) - BoxWidth, Canvas.GetTop(Base_TextBox)),
1415
                    new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox)), //위  
1416
                };
1417
                SubPathData = (Generate(pCloud));
1418
                PathDataInner = (GenerateInnerCloud(pCloud, angle));
1419
            
1420
            }//20180906 LJY Textbox guide
1421
            else
1422
            {            
1423
                List<Point> pCloud = new List<Point>()
1424
                {
1425
    #if SILVERLIGHT
1426
		            new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox)), //위
1427
                    new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox)+ BoxHeight), //왼쪽 아래
1428
                    new Point(Canvas.GetLeft(Base_TextBox)+ BoxWidth, Canvas.GetTop(Base_TextBox) + BoxHeight),
1429
                    new Point(Canvas.GetLeft(Base_TextBox) + BoxWidth, Canvas.GetTop(Base_TextBox)),
1430
                    new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox)), //위  
1431

    
1432
    #else
1433
                    new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox)), //위
1434
                    new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox)+ BoxHeight), //왼쪽 아래
1435
                    new Point(Canvas.GetLeft(Base_TextBox)+ BoxWidth, Canvas.GetTop(Base_TextBox) + BoxHeight),
1436
                    new Point(Canvas.GetLeft(Base_TextBox) + BoxWidth, Canvas.GetTop(Base_TextBox)),
1437
                    new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox)), //위  
1438

    
1439
                    //new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox)), //위
1440
                    //new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox)+ BoxHeight-4), //왼쪽 아래
1441
                    //new Point(Canvas.GetLeft(Base_TextBox)+ BoxWidth-1, Canvas.GetTop(Base_TextBox) + BoxHeight-4),
1442
                    //new Point(Canvas.GetLeft(Base_TextBox) + BoxWidth-1, Canvas.GetTop(Base_TextBox)),
1443
                    //new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox)), //위
1444
    #endif
1445
                };
1446
                //instanceGroup.Children.Add(Generate(pCloud));
1447
                SubPathData = (Generate(pCloud));
1448
                PathDataInner = (GenerateInnerCloud(pCloud, angle));
1449
                //   }
1450
            }
1451

    
1452
        }
1453

    
1454
        private void DrawingRect()
1455
        {
1456
            //20180906 LJY Textbox guide
1457
            if(this.ArrowTextStyle == ArrowTextStyleSet.Normal)
1458
            {
1459
                this.Base_TextBox.BorderBrush = Brushes.Transparent;
1460
            }
1461

    
1462
            if (Math.Abs(this.PageAngle).ToString() == "90")
1463
            {
1464
                List<Point> pCloud = new List<Point>()
1465
                {
1466
                    new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox)), //위
1467
                    new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox) - BoxWidth), //왼쪽 아래
1468
                    new Point(Canvas.GetLeft(Base_TextBox) + BoxHeight, Canvas.GetTop(Base_TextBox) - BoxWidth),
1469
                    new Point(Canvas.GetLeft(Base_TextBox) + BoxHeight, Canvas.GetTop(Base_TextBox)),
1470
                    new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox)), //위  
1471
                };
1472
                PathDataInner = (GenerateInner(pCloud));
1473
            }
1474
            else if(Math.Abs(this.PageAngle).ToString() == "270")
1475
            {
1476
                List<Point> pCloud = new List<Point>()
1477
                {
1478
                    new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox)), //위
1479
                    new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox) + BoxWidth), //왼쪽 아래
1480
                    new Point(Canvas.GetLeft(Base_TextBox) - BoxHeight, Canvas.GetTop(Base_TextBox) + BoxWidth),
1481
                    new Point(Canvas.GetLeft(Base_TextBox) - BoxHeight, Canvas.GetTop(Base_TextBox)),
1482
                    new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox)), //위  
1483
                };
1484
                PathDataInner = (GenerateInner(pCloud));
1485
            }//20180906 LJY Textbox guide
1486
            else
1487
            { 
1488
                List<Point> pCloud = new List<Point>()
1489
                {
1490
    #if SILVERLIGHT
1491
		            new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox)), //위
1492
                    new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox)+ BoxHeight), //왼쪽 아래
1493
                    new Point(Canvas.GetLeft(Base_TextBox)+ BoxWidth, Canvas.GetTop(Base_TextBox) + BoxHeight),
1494
                    new Point(Canvas.GetLeft(Base_TextBox) + BoxWidth, Canvas.GetTop(Base_TextBox)),
1495
                    new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox)), //위  
1496

    
1497
    #else
1498
                    new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox)), //위
1499
                    new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox)+ BoxHeight), //왼쪽 아래
1500
                    new Point(Canvas.GetLeft(Base_TextBox)+ BoxWidth, Canvas.GetTop(Base_TextBox) + BoxHeight),
1501
                    new Point(Canvas.GetLeft(Base_TextBox) + BoxWidth, Canvas.GetTop(Base_TextBox)),
1502
                    new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox)), //위  
1503

    
1504
                    //new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox)), //위
1505
                    //new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox)+ BoxHeight-4), //왼쪽 아래
1506
                    //new Point(Canvas.GetLeft(Base_TextBox)+ BoxWidth-1, Canvas.GetTop(Base_TextBox) + BoxHeight-4),
1507
                    //new Point(Canvas.GetLeft(Base_TextBox) + BoxWidth-1, Canvas.GetTop(Base_TextBox)),
1508
                    //new Point(Canvas.GetLeft(Base_TextBox), Canvas.GetTop(Base_TextBox)), //위
1509
    #endif
1510
                };
1511
                //instanceGroup.Children.Add(Generate(pCloud));
1512
                PathDataInner = (GenerateInner(pCloud));
1513
            }
1514
        }
1515

    
1516
        public override void UpdateControl()
1517
        {
1518
            this.StartPoint = new Point(this.PointSet[0].X, this.PointSet[0].Y);
1519
            this.MidPoint = new Point(this.PointSet[1].X, this.PointSet[1].Y);
1520
            this.EndPoint = new Point(this.PointSet[2].X, this.PointSet[2].Y);
1521
        }
1522

    
1523
        public override void ApplyOverViewData()
1524
        {
1525
            this.OverViewPathData = this.PathData;
1526
            if (ArrowText == "")
1527
                this.ArrowText = this.OverViewArrowText;
1528
            else
1529
                this.OverViewArrowText = this.ArrowText;
1530
            this.OverViewStartPoint = this.StartPoint;
1531
            this.OverViewEndPoint = this.EndPoint;
1532
        }
1533

    
1534
        #endregion
1535

    
1536
        public static PathFigure GenerateLineWithCloud(Point p1, Point p2, double arcLength_, bool reverse)
1537
        {
1538
            PathFigure pathFigure = new PathFigure();
1539
            pathFigure.StartPoint = p1;
1540

    
1541
            double arcLength = arcLength_;
1542
            /// draw arcs which has arcLength between p1 and p2 - 2012.06.21 added by humkyung 
1543
            double dx = p2.X - p1.X;
1544
            double dy = p2.Y - p1.Y;
1545
            double l = MathSet.DistanceTo(p1, p2); /// distance between p1 and p2
1546
            double theta = Math.Atan2(Math.Abs(dy), Math.Abs(dx)) * 180 / Math.PI;
1547
            Point lastPt = new Point(p1.X, p1.Y);
1548
            double count = l / arcLength;
1549
            /// normalize
1550
            dx /= l;
1551
            dy /= l;
1552
            Double j = 1;
1553
            for (j = 1; j < (count - 1); j++) 
1554
            {
1555
                ArcSegment arcSeg = new ArcSegment();
1556
                arcSeg.Size = new Size(arcLength * _CloudArcDepth, arcLength * _CloudArcDepth);						/// x size and y size of arc
1557
                arcSeg.Point = new Point(p1.X + j * dx * arcLength, p1.Y + j * dy * arcLength);	/// end point of arc
1558
                lastPt = arcSeg.Point;  /// save last point
1559
                arcSeg.RotationAngle = theta + 90;
1560
                if (true == reverse) arcSeg.SweepDirection = SweepDirection.Clockwise;
1561
                pathFigure.Segments.Add(arcSeg);
1562
            }
1563

    
1564
            /// draw arc between last point and end point
1565
            if ((count > j) || (count > 0))
1566
            {
1567
                arcLength = MathSet.DistanceTo(lastPt, p2);
1568
                ArcSegment arcSeg = new ArcSegment();
1569
                arcSeg.Size = new Size(arcLength * _CloudArcDepth, arcLength * _CloudArcDepth);	/// x size and y size of arc
1570
                arcSeg.Point = new Point(p2.X, p2.Y);						/// end point of arc
1571
                arcSeg.RotationAngle = theta;
1572
                if (true == reverse) arcSeg.SweepDirection = SweepDirection.Clockwise;
1573
                pathFigure.Segments.Add(arcSeg);
1574
            }
1575
            /// up to here
1576

    
1577
            return pathFigure;
1578
        }
1579

    
1580
        public static PathGeometry Generate(List<Point> pData)
1581
        {
1582
            var _pathGeometry = new PathGeometry();
1583
            
1584
            double area = MathSet.AreaOf(pData);
1585
            bool reverse = (area > 0);
1586
            int count = pData.Count;
1587
            for (int i = 0; i < (count - 1); i++)
1588
            {
1589
                PathFigure pathFigure = GenerateLineWithCloud(pData[i], pData[i + 1], 20, reverse);
1590
                pathFigure.IsClosed = false;
1591
                pathFigure.IsFilled = true;
1592
                _pathGeometry.Figures.Add(pathFigure);
1593
            }
1594
            
1595
            return _pathGeometry;
1596
        }
1597

    
1598
        
1599
        public static PathGeometry GenerateInner(List<Point> pData)
1600
        {
1601
            var _pathGeometry = new PathGeometry();
1602
            double area = MathSet.AreaOf(pData);
1603
            bool reverse = (area > 0);
1604
            int count = pData.Count;
1605

    
1606
            PathFigure pathFigur2 = new PathFigure();
1607
            pathFigur2.StartPoint = pData[0];
1608

    
1609
            LineSegment lineSegment0 = new LineSegment();
1610
            lineSegment0.Point = pData[0];
1611
            pathFigur2.Segments.Add(lineSegment0);
1612

    
1613
            LineSegment lineSegment1 = new LineSegment();
1614
            lineSegment1.Point = pData[1];
1615
            pathFigur2.Segments.Add(lineSegment1);
1616

    
1617
            LineSegment lineSegment2 = new LineSegment();
1618
            lineSegment2.Point = pData[2];
1619
            pathFigur2.Segments.Add(lineSegment2);
1620

    
1621
            LineSegment lineSegment3 = new LineSegment();
1622
            lineSegment3.Point = pData[3];
1623
            pathFigur2.Segments.Add(lineSegment3);
1624

    
1625

    
1626
            pathFigur2.IsClosed = true;
1627
            pathFigur2.IsFilled = true;
1628
            _pathGeometry.Figures.Add(pathFigur2);           
1629

    
1630
            return _pathGeometry;
1631
        }
1632

    
1633
        //20180910 LJY Cloud rotation 추가
1634
        public static PathGeometry GenerateInnerCloud(List<Point> pData, string angle)
1635
        {
1636
            var _pathGeometry = new PathGeometry();
1637
            double area = MathSet.AreaOf(pData);
1638
            bool reverse = (area > 0);
1639
            int count = pData.Count;
1640

    
1641
            PathFigure pathFigur2 = new PathFigure();
1642
            pathFigur2.StartPoint = pData[0];
1643

    
1644
            LineSegment lineSegment0 = new LineSegment();
1645
            lineSegment0.Point = pData[0];
1646
            pathFigur2.Segments.Add(lineSegment0);
1647

    
1648
            LineSegment lineSegment1 = new LineSegment();
1649
            lineSegment1.Point = pData[1];
1650
            pathFigur2.Segments.Add(lineSegment1);
1651

    
1652
            LineSegment lineSegment2 = new LineSegment();
1653
            lineSegment2.Point = pData[2];
1654
            pathFigur2.Segments.Add(lineSegment2);
1655

    
1656
            LineSegment lineSegment3 = new LineSegment();
1657
            lineSegment3.Point = pData[3];
1658
            pathFigur2.Segments.Add(lineSegment3);
1659
            
1660
            RotateTransform transform = new RotateTransform();
1661
            switch (angle)
1662
            {
1663
                case "90":
1664
                    transform.Angle = -90;
1665
                    break;
1666
                case "180":
1667
                    transform.Angle = -180;
1668
                    break;
1669
                case "270":
1670
                    transform.Angle = -270;
1671
                    break;
1672
            }
1673
            transform.CenterX = pData[0].X;
1674
            transform.CenterY = pData[0].Y;
1675
            _pathGeometry.Transform = transform;
1676

    
1677
            pathFigur2.IsClosed = true;
1678
            pathFigur2.IsFilled = true;
1679
            _pathGeometry.Figures.Add(pathFigur2);
1680

    
1681
            return _pathGeometry;
1682
        }
1683

    
1684
        /// <summary>
1685
        /// call when mouse is moving while drawing control
1686
        /// </summary>
1687
        /// <author>humkyung</author>
1688
        /// <param name="pt"></param>
1689
        /// <param name="bAxisLocked"></param>
1690
        public override void OnCreatingMouseMove(Point pt, bool bAxisLocked)
1691
        {
1692
            this.EndPoint = pt;
1693

    
1694
            Point tempPoint = this.EndPoint;
1695
            CommentAngle = MathSet.returnAngle(this.StartPoint, ref tempPoint, bAxisLocked);
1696

    
1697
            if (bAxisLocked)
1698
            {
1699
                this.EndPoint = tempPoint;
1700
            }
1701

    
1702
            this.MidPoint = MathSet.getMiddlePoint(this.StartPoint, this.EndPoint);
1703
            this.isFixed = (this.ControlType == ControlType.ArrowTransTextControl) || 
1704
                (this.ControlType == ControlType.ArrowTransTextBorderControl) || (this.ControlType == ControlType.ArrowTransTextCloudControl);
1705

    
1706
            this.PointSet = new List<Point>
1707
            {
1708
                this.StartPoint,
1709
                this.MidPoint,
1710
                this.EndPoint,
1711
            };
1712
        }
1713

    
1714
        /// <summary>
1715
        /// move control point has same location of given pt along given delta
1716
        /// </summary>
1717
        /// <author>humkyung</author>
1718
        /// <date>2019.06.20</date>
1719
        /// <param name="pt"></param>
1720
        /// <param name="dx"></param>
1721
        /// <param name="dy"></param>
1722
        public override void OnMoveCtrlPoint(Point pt, double dx, double dy, bool bAxisLocked = false)
1723
        {
1724
            IPath path = (this as IPath);
1725

    
1726
            //System.Diagnostics.Debug.WriteLine($"OnMoveCtrlPoint : {path.PointSet[1].X},{path.PointSet[1].Y}");
1727

    
1728
            Point selected = MathSet.getNearPoint(path.PointSet, pt);
1729

    
1730
            //StartPoint에 표시된 Thumb는 dx,dy가 +로 더해줘야한다.
1731
            if (path.PointSet.IndexOf(selected) != 0)
1732
            {
1733
                double radian = this.CommentAngle * Math.PI / 180;
1734
                double cos = Math.Cos(radian);
1735
                double sin = Math.Sin(radian);
1736

    
1737
                double _dx = dx * cos - dy * sin;
1738
                double _dy = dx * sin + dy * cos;
1739

    
1740
                selected.X += _dx;
1741
                selected.Y += _dy;
1742
            }
1743
            else
1744
            {
1745
                selected.X += dx;
1746
                selected.Y += dy;
1747
            }
1748

    
1749
            int i = 0;
1750
            for (i = 0; i < (this as IPath).PointSet.Count; i++)
1751
            {
1752
                if (pt.Equals((this as IPath).PointSet[i])) break;
1753
            }
1754

    
1755
            List<Point> pts = path.PointSet;
1756
            if ((pts[0].X > pts[1].X && dx > 0) || (pts[0].X < pts[1].X && dx < 0))
1757
            {
1758
                pts[1] = new Point(pts[1].X + dx, pts[1].Y);
1759
            }
1760
            if ((pts[0].Y > pts[1].Y && dy > 0) || (pts[0].Y < pts[1].Y && dy < 0))
1761
            {
1762
                pts[1] = new Point(pts[1].X, pts[1].Y + dy);
1763
            }
1764

    
1765
            path.PointSet[1] = pts[1];
1766

    
1767
            if (path.PointSet.Count > i) {
1768
                path.PointSet[i] = selected;
1769
            }
1770
            //System.Diagnostics.Debug.WriteLine($"OnMoveCtrlPoint end : {path.PointSet[1].X},{path.PointSet[1].Y}");
1771
            this.UpdateControl();
1772
        }
1773

    
1774
        /// <summary>
1775
        /// return ArrowTextControl's area
1776
        /// </summary>
1777
        /// <author>humkyung</author>
1778
        /// <date>2019.06.13</date>
1779
        public override Rect ItemRect
1780
        {
1781
            get
1782
            {
1783
                double dMinX = Math.Min(this.StartPoint.X, this.EndPoint.X);
1784
                double dMinY = Math.Min(this.StartPoint.Y, this.EndPoint.Y);
1785
                double dMaxX = Math.Max(this.StartPoint.X, this.EndPoint.X);
1786
                double dMaxY = Math.Max(this.StartPoint.Y, this.EndPoint.Y);
1787

    
1788
                return new Rect(new Point(dMinX, dMinY), new Point(dMaxX, dMaxY));
1789
            }
1790
        }
1791

    
1792
        /// <summary>
1793
        /// Serialize this
1794
        /// </summary>
1795
        /// <param name="sUserId"></param>
1796
        /// <returns></returns>
1797
        public override string Serialize()
1798
        {
1799
            using (S_ArrowTextControl STemp = new S_ArrowTextControl())
1800
            {
1801
                STemp.TransformPoint = "0|0";
1802
                STemp.PointSet = this.PointSet;
1803
                STemp.SizeSet = String.Format("{0}", this.LineSize);
1804
                STemp.StrokeColor = this.StrokeColor.Color.ToString();
1805
                STemp.StartPoint = this.StartPoint;
1806
                STemp.ArrowStyle = this.ArrowTextStyle;
1807
                //STemp.StrokeColor = "#FF00FF00";
1808
                STemp.UserID = this.UserID;
1809
                STemp.ArrowText = this.Base_TextBox.Text;
1810
                STemp.BorderSize = this.BorderSize;
1811
                STemp.isHighLight = this.isHighLight;
1812
                STemp.BoxHeight = this.BoxHeight;
1813
                STemp.BoxWidth = this.BoxWidth;
1814
                STemp.Opac = this.Opacity;
1815
                STemp.EndPoint = this.EndPoint;
1816
                STemp.isFixed = this.isFixed;
1817
                //STemp.DashSize = this.DashSize;
1818
                STemp.Name = this.GetType().Name.ToString();
1819
                STemp.isTrans = this.isTrans;
1820
                STemp.MidPoint = this.MidPoint;
1821
                STemp.Angle = this.PageAngle;
1822
                STemp.fontConfig = new List<string>()
1823
                            {
1824
                                this.TextFamily.FontName(),
1825
                                this.TextStyle.ToString(),
1826
                                this.TextWeight.ToString(),
1827
                                this.TextSize.ToString(),
1828
                            };
1829

    
1830
                if (this.UnderLine != null)
1831
                {
1832
                    STemp.fontConfig.Add("true");
1833
                }
1834

    
1835
                ///강인구 추가(2017.11.02)
1836
                ///Memo 추가
1837
                STemp.Memo = this.Memo;
1838
                STemp.BorderSize = this.BorderSize;
1839
                return "|DZ|" + JsonSerializerHelper.CompressString((STemp.JsonSerialize()));
1840
            };
1841
        }
1842

    
1843
        /// <summary>
1844
        /// create a arrowtextcontrol from given string
1845
        /// </summary>
1846
        /// <param name="str"></param>
1847
        /// <returns></returns>
1848
        public static ArrowTextControl FromString(string str, SolidColorBrush brush, string sProjectNo)
1849
        {
1850
            ArrowTextControl instance = null;
1851
            using (S_ArrowTextControl s = JsonSerializerHelper.JsonDeserialize<S_ArrowTextControl>(str))
1852
            {
1853
                string[] data2 = s.SizeSet.Split(delimiterChars2, StringSplitOptions.RemoveEmptyEntries);
1854
                instance = new ArrowTextControl();
1855
                instance.LineSize = Convert.ToDouble(data2.First());
1856
                instance.PointSet = s.PointSet;
1857
                instance.StartPoint = s.StartPoint;
1858
                instance.EndPoint = s.EndPoint;
1859
                instance.StrokeColor = brush;
1860
                //instance.DashSize = s.DashSize;
1861
                instance.ArrowTextStyle = s.ArrowStyle;
1862
                instance.isHighLight = s.isHighLight;
1863
                instance.ArrowText = s.ArrowText;
1864
                instance.Opacity = s.Opac;
1865
                instance.BorderSize = s.BorderSize;
1866
                instance.BoxWidth = s.BoxWidth;
1867
                instance.BoxHeight = s.BoxHeight;
1868
                instance.isFixed = s.isFixed;
1869
                instance.PageAngle = s.Angle;
1870
                instance.UserID = s.UserID;
1871
                instance.isTrans = s.isTrans;
1872
                instance.MidPoint = s.MidPoint;
1873
                instance.Memo = s.Memo;
1874
                if (s.fontConfig == null || s.fontConfig.ToList().Count == 0)
1875
                {
1876
                    s.fontConfig = new List<string>();
1877

    
1878
                    s.fontConfig.Add("Arial");
1879
                    s.fontConfig.Add("Normal");
1880
                    s.fontConfig.Add("Normal");
1881
                    s.fontConfig.Add("30");
1882
                }
1883
                instance.TextFamily = Markus.Fonts.FontHelper.GetFontFamily(s.fontConfig[0]);
1884
                //인구 추가(2018.04.17)
1885
                instance.TextStyle = StringToFont.ConFontStyle(s.fontConfig[1]);
1886
                instance.TextWeight = StringToFont.ConFontWeight(s.fontConfig[2]);
1887
                instance.TextSize = Convert.ToDouble(s.fontConfig[3]);
1888

    
1889
                if (s.fontConfig.Count() == 5)
1890
                {
1891
                    instance.UnderLine = TextDecorations.Underline;
1892
                }
1893
            }
1894

    
1895
            return instance;
1896
        }
1897

    
1898
        #region Dispose
1899
        public void Dispose()
1900
        {
1901
            //GC.Collect();
1902
            ////GC.SuppressFinalize(this);
1903
            this.BaseTextbox_Caret = null;
1904
            this.Base_ArrowPath = null;
1905
            this.Base_ArrowSubPath = null;
1906
            this.Base_TextBlock = null;
1907
            this.Base_TextBox = null;
1908
        } 
1909
        #endregion
1910

    
1911
        #region INotifyPropertyChanged
1912
        private void OnPropertyChanged(string name)
1913
        {
1914
            if (PropertyChanged != null)
1915
            {
1916
                PropertyChanged(this, new PropertyChangedEventArgs(name));
1917
            }
1918
        }
1919

    
1920
        public event PropertyChangedEventHandler PropertyChanged; 
1921
        #endregion
1922
    }
1923
}
클립보드 이미지 추가 (최대 크기: 500 MB)