[NUI] Fixing the emtpy finalizers(CA1821)
[platform/core/csapi/tizenfx.git] / src / Tizen.NUI / src / public / FocusManager.cs
1 /*
2  * Copyright(c) 2019 Samsung Electronics Co., Ltd.
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  *
16  */
17
18 using System;
19 using System.Runtime.InteropServices;
20 using Tizen.NUI.BaseComponents;
21 using System.ComponentModel;
22
23 namespace Tizen.NUI
24 {
25     /// <summary>
26     /// Provides the functionality of handling keyboard navigation and maintaining the two-dimensional keyboard focus chain.<br />
27     /// It provides functionality of setting the focus and moving the focus in four directions( i.e., left, right, up, and down).<br />
28     /// It also draws a highlight for the focused view and sends an event when the focus is changed.<br />
29     /// </summary>
30     /// <since_tizen> 3 </since_tizen>
31     public class FocusManager : BaseHandle
32     {
33         private static readonly FocusManager instance = FocusManager.Get();
34         private CustomAlgorithmInterfaceWrapper _customAlgorithmInterfaceWrapper;
35
36         private EventHandlerWithReturnType<object, PreFocusChangeEventArgs, View> _preFocusChangeEventHandler;
37         private PreFocusChangeEventCallback _preFocusChangeCallback;
38
39         private EventHandler<FocusChangedEventArgs> _focusChangedEventHandler;
40         private FocusChangedEventCallback _focusChangedEventCallback;
41
42         private EventHandler<FocusGroupChangedEventArgs> _focusGroupChangedEventHandler;
43         private FocusGroupChangedEventCallback _focusGroupChangedEventCallback;
44
45         private EventHandler<FocusedViewActivatedEventArgs> _focusedViewEnterKeyEventHandler;
46         private FocusedViewEnterKeyEventCallback _focusedViewEnterKeyEventCallback;
47
48         private EventHandler<FocusedViewActivatedEventArgs> _focusedViewEnterKeyEventHandler2;
49         private FocusedViewEnterKeyEventCallback2 _focusedViewEnterKeyEventCallback2;
50
51         internal FocusManager(global::System.IntPtr cPtr, bool cMemoryOwn) : base(Interop.FocusManager.Upcast(cPtr), cMemoryOwn)
52         {
53         }
54
55         internal FocusManager() : this(Interop.FocusManager.NewFocusManager(), true)
56         {
57             if (NDalicPINVOKE.SWIGPendingException.Pending) throw NDalicPINVOKE.SWIGPendingException.Retrieve();
58         }
59
60         [UnmanagedFunctionPointer(CallingConvention.StdCall)]
61         internal delegate IntPtr PreFocusChangeEventCallback(IntPtr current, IntPtr proposed, View.FocusDirection direction);
62
63         [UnmanagedFunctionPointer(CallingConvention.StdCall)]
64         internal delegate void FocusChangedEventCallback(IntPtr current, IntPtr next);
65
66         [UnmanagedFunctionPointer(CallingConvention.StdCall)]
67         private delegate void FocusGroupChangedEventCallback(IntPtr current, bool forwardDirection);
68
69         [UnmanagedFunctionPointer(CallingConvention.StdCall)]
70         private delegate void FocusedViewEnterKeyEventCallback(IntPtr view);
71
72         [UnmanagedFunctionPointer(CallingConvention.StdCall)]
73         private delegate void FocusedViewEnterKeyEventCallback2(IntPtr view);
74
75         /// <summary>
76         /// PreFocusChange will be triggered before the focus is going to be changed.<br />
77         /// The FocusManager makes the best guess for which view to focus towards the given direction, but applications might want to change that.<br />
78         /// By connecting with this event, they can check the proposed view to focus and return a different view if they wish.<br />
79         /// This event is only triggered when the navigation key is pressed and KeyboardFocusManager tries to move the focus automatically.<br />
80         /// It won't be emitted for focus movement by calling the SetCurrentFocusView directly.<br />
81         /// </summary>
82         /// <since_tizen> 3 </since_tizen>
83         public event EventHandlerWithReturnType<object, PreFocusChangeEventArgs, View> PreFocusChange
84         {
85             add
86             {
87                 if (_preFocusChangeEventHandler == null)
88                 {
89                     _preFocusChangeCallback = OnPreFocusChange;
90                     PreFocusChangeSignal().Connect(_preFocusChangeCallback);
91                 }
92                 _preFocusChangeEventHandler += value;
93             }
94             remove
95             {
96                 _preFocusChangeEventHandler -= value;
97                 if (_preFocusChangeEventHandler == null && PreFocusChangeSignal().Empty() == false)
98                 {
99                     PreFocusChangeSignal().Disconnect(_preFocusChangeCallback);
100                 }
101             }
102         }
103
104         /// <summary>
105         /// The FocusGroupChanged will be triggered after the current focused view has been changed.
106         /// </summary>
107         /// <since_tizen> 3 </since_tizen>
108         public event EventHandler<FocusChangedEventArgs> FocusChanged
109         {
110             add
111             {
112                 if (_focusChangedEventCallback == null)
113                 {
114                     _focusChangedEventCallback = OnFocusChanged;
115                     FocusChangedSignal().Connect(_focusChangedEventCallback);
116                 }
117                 _focusChangedEventHandler += value;
118             }
119             remove
120             {
121                 _focusChangedEventHandler -= value;
122
123                 if (_focusChangedEventCallback == null && FocusChangedSignal().Empty() == false)
124                 {
125                     FocusChangedSignal().Disconnect(_focusChangedEventCallback);
126                 }
127             }
128         }
129
130         /// <summary>
131         /// The FocusGroupChanged will be triggered when the focus group has been changed.<br />
132         /// If the current focus group has a parent layout control, the FocusManager will make the best guess for the next focus group to move the focus to in the given direction (forward or backward).<br />
133         /// If not, the application has to set the new focus.<br />
134         /// </summary>
135         /// <since_tizen> 3 </since_tizen>
136         public event EventHandler<FocusGroupChangedEventArgs> FocusGroupChanged
137         {
138             add
139             {
140                 if (_focusGroupChangedEventCallback == null)
141                 {
142                     _focusGroupChangedEventCallback = OnFocusGroupChanged;
143                     FocusGroupChangedSignal().Connect(_focusGroupChangedEventCallback);
144                 }
145                 _focusGroupChangedEventHandler += value;
146             }
147             remove
148             {
149                 _focusGroupChangedEventHandler -= value;
150
151                 if (_focusGroupChangedEventCallback == null && FocusGroupChangedSignal().Empty() == false)
152                 {
153                     FocusGroupChangedSignal().Disconnect(_focusGroupChangedEventCallback);
154                 }
155             }
156         }
157
158         /// <summary>
159         /// The FocusedViewActivated will be triggered when the current focused view has the enter key pressed on it.
160         /// </summary>
161         /// <since_tizen> 3 </since_tizen>
162         public event EventHandler<FocusedViewActivatedEventArgs> FocusedViewActivated
163         {
164             add
165             {
166                 if (_focusedViewEnterKeyEventCallback == null)
167                 {
168                     _focusedViewEnterKeyEventCallback = OnFocusedViewEnterKey;
169                     FocusedViewEnterKeySignal().Connect(_focusedViewEnterKeyEventCallback);
170                 }
171                 _focusedViewEnterKeyEventHandler += value;
172             }
173             remove
174             {
175                 _focusedViewEnterKeyEventHandler -= value;
176
177                 if (_focusedViewEnterKeyEventCallback != null && FocusedViewEnterKeySignal().Empty() == false)
178                 {
179                     FocusedViewEnterKeySignal().Disconnect(_focusedViewEnterKeyEventCallback);
180                 }
181             }
182         }
183
184         /// <summary>
185         /// [Obsolete("Please do not use! this will be deprecated")]
186         /// </summary>
187         /// <since_tizen> 3 </since_tizen>
188         /// Please do not use! this will be deprecated!
189         /// Instead please use FocusedViewActivated.
190         [Obsolete("Please do not use! This will be deprecated! Please use FocusManager.FocusedViewActivated instead! " +
191             "Like: " +
192             "FocusManager.Instance.FocusedViewActivated = OnFocusedViewActivated; " +
193             "private void OnFocusedViewActivated(object source, FocusManager.FocusedViewActivatedEventArgs args) {...}")]
194         [EditorBrowsable(EditorBrowsableState.Never)]
195         public event EventHandler<FocusedViewActivatedEventArgs> FocusedViewEnterKeyPressed
196         {
197             add
198             {
199                 if (_focusedViewEnterKeyEventCallback2 == null)
200                 {
201                     _focusedViewEnterKeyEventCallback2 = OnFocusedViewEnterKey2;
202                     FocusedViewEnterKeySignal().Connect(_focusedViewEnterKeyEventCallback2);
203                 }
204                 _focusedViewEnterKeyEventHandler2 += value;
205             }
206             remove
207             {
208                 _focusedViewEnterKeyEventHandler2 -= value;
209
210                 if (_focusedViewEnterKeyEventCallback2 != null && FocusedViewEnterKeySignal().Empty() == false)
211                 {
212                     FocusedViewEnterKeySignal().Disconnect(_focusedViewEnterKeyEventCallback2);
213                 }
214             }
215         }
216
217         /// <summary>
218         /// ICustomFocusAlgorithm is used to provide the custom keyboard focus algorithm for retrieving the next focusable view.<br />
219         /// The application can implement the interface and override the keyboard focus behavior.<br />
220         /// If the focus is changing within a layout container, then the layout container is queried first to provide the next focusable view.<br />
221         /// If this does not provide a valid view, then the Keyboard FocusManager will check focusable properties to determine the next focusable actor.<br />
222         /// If focusable properties are not set, then the keyboard FocusManager calls the GetNextFocusableView() method of this interface.<br />
223         /// </summary>
224         /// <since_tizen> 3 </since_tizen>
225         public interface ICustomFocusAlgorithm
226         {
227             /// <summary>
228             /// Get the next focus actor.
229             /// </summary>
230             /// <param name="current">The current focus view.</param>
231             /// <param name="proposed">The proposed focus view</param>
232             /// <param name="direction">The focus move direction</param>
233             /// <returns>The next focus actor.</returns>
234             /// <since_tizen> 3 </since_tizen>
235             View GetNextFocusableView(View current, View proposed, View.FocusDirection direction);
236         }
237
238         /// <summary>
239         /// Gets or sets the status of whether the focus movement should be looped within the same focus group.<br />
240         /// The focus movement is not looped by default.<br />
241         /// </summary>
242         /// <since_tizen> 3 </since_tizen>
243         public bool FocusGroupLoop
244         {
245             set
246             {
247                 SetFocusGroupLoop(value);
248             }
249             get
250             {
251                 return GetFocusGroupLoop();
252             }
253         }
254
255         /// <summary>
256         /// Gets or sets the focus indicator view.<br />
257         /// This will replace the default focus indicator view in the FocusManager and will be added to the focused view as a highlight.<br />
258         /// </summary>
259         /// <since_tizen> 3 </since_tizen>
260         public View FocusIndicator
261         {
262             set
263             {
264                 SetFocusIndicatorView(value);
265             }
266             get
267             {
268                 return GetFocusIndicatorView();
269             }
270         }
271
272         /// <summary>
273         /// Gets the singleton of the FocusManager object.
274         /// </summary>
275         /// <since_tizen> 3 </since_tizen>
276         public static FocusManager Instance
277         {
278             get
279             {
280                 return instance;
281             }
282         }
283
284         /// <summary>
285         /// Moves the keyboard focus to the given view.<br />
286         /// Only one view can be focused at the same time.<br />
287         /// The view must be in the stage already and keyboard focusable.<br />
288         /// </summary>
289         /// <param name="view">The view to be focused.</param>
290         /// <returns>Whether the focus is successful or not.</returns>
291         /// <since_tizen> 3 </since_tizen>
292         public bool SetCurrentFocusView(View view)
293         {
294             if (view == null)
295             {
296                 throw new ArgumentNullException(nameof(view), "the target view should not be null");
297             }
298
299             bool ret = Interop.FocusManager.SetCurrentFocusActor(SwigCPtr, View.getCPtr(view));
300             if (NDalicPINVOKE.SWIGPendingException.Pending) throw NDalicPINVOKE.SWIGPendingException.Retrieve();
301             return ret;
302         }
303
304         /// <summary>
305         /// Gets the current focused view.
306         /// </summary>
307         /// <returns>A handle to the current focused view or an empty handle if no view is focused.</returns>
308         /// <since_tizen> 3 </since_tizen>
309         public View GetCurrentFocusView()
310         {
311             //to fix memory leak issue, match the handle count with native side.
312             IntPtr cPtr = Interop.FocusManager.GetCurrentFocusActor(SwigCPtr);
313             View ret = this.GetInstanceSafely<View>(cPtr);
314             return ret;
315         }
316
317         /// <summary>
318         /// Moves the focus to the next focusable view in the focus chain in the given direction (according to the focus traversal order).
319         /// </summary>
320         /// <param name="direction">The direction of the focus movement.</param>
321         /// <returns>True if the movement was successful.</returns>
322         /// <since_tizen> 3 </since_tizen>
323         public bool MoveFocus(View.FocusDirection direction)
324         {
325             bool ret = Interop.FocusManager.MoveFocus(SwigCPtr, (int)direction);
326             if (NDalicPINVOKE.SWIGPendingException.Pending) throw NDalicPINVOKE.SWIGPendingException.Retrieve();
327             return ret;
328         }
329
330         /// <summary>
331         /// Clears the focus from the current focused view if any, so that no view is focused in the focus chain.<br />
332         /// It will emit the FocusChanged event without the current focused view.<br />
333         /// </summary>
334         /// <since_tizen> 3 </since_tizen>
335         public void ClearFocus()
336         {
337             Interop.FocusManager.ClearFocus(SwigCPtr);
338             if (NDalicPINVOKE.SWIGPendingException.Pending) throw NDalicPINVOKE.SWIGPendingException.Retrieve();
339         }
340
341         /// <summary>
342         /// Move the focus to previous focused view.
343         /// </summary>
344         /// <since_tizen> 3 </since_tizen>
345         public void MoveFocusBackward()
346         {
347             Interop.FocusManager.MoveFocusBackward(SwigCPtr);
348             if (NDalicPINVOKE.SWIGPendingException.Pending) throw NDalicPINVOKE.SWIGPendingException.Retrieve();
349         }
350
351         /// <summary>
352         /// Sets whether the view is a focus group that can limit the scope of the focus movement to its child views in the focus chain.<br />
353         /// Layout controls set themselves as focus groups by default.<br />
354         /// </summary>
355         /// <param name="view">The view to be set as a focus group.</param>
356         /// <param name="isFocusGroup">Whether to set the view as a focus group or not.</param>
357         /// <since_tizen> 3 </since_tizen>
358         public void SetAsFocusGroup(View view, bool isFocusGroup)
359         {
360             Interop.FocusManager.SetAsFocusGroup(SwigCPtr, View.getCPtr(view), isFocusGroup);
361             if (NDalicPINVOKE.SWIGPendingException.Pending) throw NDalicPINVOKE.SWIGPendingException.Retrieve();
362         }
363
364         /// <summary>
365         /// Checks whether the view is set as a focus group or not.
366         /// </summary>
367         /// <param name="view">The view to be checked.</param>
368         /// <returns>Whether the view is set as a focus group.</returns>
369         /// <since_tizen> 3 </since_tizen>
370         public bool IsFocusGroup(View view)
371         {
372             bool ret = Interop.FocusManager.IsFocusGroup(SwigCPtr, View.getCPtr(view));
373             if (NDalicPINVOKE.SWIGPendingException.Pending) throw NDalicPINVOKE.SWIGPendingException.Retrieve();
374             return ret;
375         }
376
377         /// <summary>
378         /// Returns the closest ancestor of the given view that is a focus group.
379         /// </summary>
380         /// <param name="view">The view to be checked for its focus group.</param>
381         /// <returns>The focus group the given view belongs to or an empty handle if the given view.</returns>
382         /// <since_tizen> 3 </since_tizen>
383         public View GetFocusGroup(View view)
384         {
385             //to fix memory leak issue, match the handle count with native side.
386             IntPtr cPtr = Interop.FocusManager.GetFocusGroup(SwigCPtr, View.getCPtr(view));
387             View ret = this.GetInstanceSafely<View>(cPtr);
388             return ret;
389         }
390
391         /// <summary>
392         /// Provides the implementation of a custom focus algorithm interface to allow the application to define the focus logic.<br />
393         /// </summary>
394         /// <param name="arg0">The user's implementation of ICustomFocusAlgorithm.</param>
395         /// <since_tizen> 3 </since_tizen>
396         public void SetCustomAlgorithm(ICustomFocusAlgorithm arg0)
397         {
398             if (arg0 != null)
399             {
400                 _customAlgorithmInterfaceWrapper = new CustomAlgorithmInterfaceWrapper();
401                 _customAlgorithmInterfaceWrapper.SetFocusAlgorithm(arg0);
402
403                 Interop.NDalic.SetCustomAlgorithm(SwigCPtr, CustomAlgorithmInterface.getCPtr(_customAlgorithmInterfaceWrapper));
404                 if (NDalicPINVOKE.SWIGPendingException.Pending) throw NDalicPINVOKE.SWIGPendingException.Retrieve();
405             }
406             else
407             {
408                 Interop.NDalic.SetCustomAlgorithm(SwigCPtr, new global::System.Runtime.InteropServices.HandleRef(null, global::System.IntPtr.Zero));
409                 if (NDalicPINVOKE.SWIGPendingException.Pending) throw NDalicPINVOKE.SWIGPendingException.Retrieve();
410             }
411         }
412
413         internal static FocusManager Get()
414         {
415             FocusManager ret = new FocusManager(Interop.FocusManager.Get(), true);
416             if (NDalicPINVOKE.SWIGPendingException.Pending) throw NDalicPINVOKE.SWIGPendingException.Retrieve();
417             return ret;
418         }
419
420         internal void SetFocusGroupLoop(bool enabled)
421         {
422             Interop.FocusManager.SetFocusGroupLoop(SwigCPtr, enabled);
423             if (NDalicPINVOKE.SWIGPendingException.Pending) throw NDalicPINVOKE.SWIGPendingException.Retrieve();
424         }
425
426         internal bool GetFocusGroupLoop()
427         {
428             bool ret = Interop.FocusManager.GetFocusGroupLoop(SwigCPtr);
429             if (NDalicPINVOKE.SWIGPendingException.Pending) throw NDalicPINVOKE.SWIGPendingException.Retrieve();
430             return ret;
431         }
432
433         internal void SetFocusIndicatorView(View indicator)
434         {
435             Interop.FocusManager.SetFocusIndicatorActor(SwigCPtr, View.getCPtr(indicator));
436             if (NDalicPINVOKE.SWIGPendingException.Pending) throw NDalicPINVOKE.SWIGPendingException.Retrieve();
437         }
438
439         internal View GetFocusIndicatorView()
440         {
441             //to fix memory leak issue, match the handle count with native side.
442             IntPtr cPtr = Interop.FocusManager.GetFocusIndicatorActor(SwigCPtr);
443             View ret = this.GetInstanceSafely<View>(cPtr);
444             return ret;
445         }
446
447         internal PreFocusChangeSignal PreFocusChangeSignal()
448         {
449             PreFocusChangeSignal ret = new PreFocusChangeSignal(Interop.FocusManager.PreFocusChangeSignal(SwigCPtr), false);
450             if (NDalicPINVOKE.SWIGPendingException.Pending) throw NDalicPINVOKE.SWIGPendingException.Retrieve();
451             return ret;
452         }
453
454         internal FocusChangedSignal FocusChangedSignal()
455         {
456             FocusChangedSignal ret = new FocusChangedSignal(Interop.FocusManager.FocusChangedSignal(SwigCPtr), false);
457             if (NDalicPINVOKE.SWIGPendingException.Pending) throw NDalicPINVOKE.SWIGPendingException.Retrieve();
458             return ret;
459         }
460
461         internal FocusGroupChangedSignal FocusGroupChangedSignal()
462         {
463             FocusGroupChangedSignal ret = new FocusGroupChangedSignal(Interop.FocusManager.FocusGroupChangedSignal(SwigCPtr), false);
464             if (NDalicPINVOKE.SWIGPendingException.Pending) throw NDalicPINVOKE.SWIGPendingException.Retrieve();
465             return ret;
466         }
467
468         internal ViewSignal FocusedViewEnterKeySignal()
469         {
470             ViewSignal ret = new ViewSignal(Interop.FocusManager.FocusedActorEnterKeySignal(SwigCPtr), false);
471             if (NDalicPINVOKE.SWIGPendingException.Pending) throw NDalicPINVOKE.SWIGPendingException.Retrieve();
472             return ret;
473         }
474
475         private IntPtr OnPreFocusChange(IntPtr current, IntPtr proposed, View.FocusDirection direction)
476         {
477             View view = null;
478             PreFocusChangeEventArgs e = new PreFocusChangeEventArgs();
479
480             if (current != global::System.IntPtr.Zero)
481             {
482                 e.CurrentView = Registry.GetManagedBaseHandleFromNativePtr(current) as View;
483             }
484             if (proposed != global::System.IntPtr.Zero)
485             {
486                 e.ProposedView = Registry.GetManagedBaseHandleFromNativePtr(proposed) as View;
487             }
488             e.Direction = direction;
489
490             if (_preFocusChangeEventHandler != null)
491             {
492                 view = _preFocusChangeEventHandler(this, e);
493             }
494
495             if (view != null)
496             {
497                 return view.GetPtrfromView();
498             }
499             else
500             {
501                 if (e.ProposedView) return proposed;
502                 else return current;
503             }
504         }
505
506         private void OnFocusChanged(IntPtr current, IntPtr next)
507         {
508             FocusChangedEventArgs e = new FocusChangedEventArgs();
509
510             e.CurrentView = Registry.GetManagedBaseHandleFromNativePtr(current) as View;
511             e.NextView = Registry.GetManagedBaseHandleFromNativePtr(next) as View;
512
513             if (_focusChangedEventHandler != null)
514             {
515                 _focusChangedEventHandler(this, e);
516             }
517         }
518
519         private void OnFocusGroupChanged(IntPtr current, bool forwardDirection)
520         {
521             FocusGroupChangedEventArgs e = new FocusGroupChangedEventArgs();
522
523             e.CurrentView = Registry.GetManagedBaseHandleFromNativePtr(current) as View;
524             e.ForwardDirection = forwardDirection;
525
526             if (_focusGroupChangedEventHandler != null)
527             {
528                 _focusGroupChangedEventHandler(this, e);
529             }
530         }
531
532         private void OnFocusedViewEnterKey(IntPtr view)
533         {
534             FocusedViewActivatedEventArgs e = new FocusedViewActivatedEventArgs();
535
536             e.View = Registry.GetManagedBaseHandleFromNativePtr(view) as View;
537
538             if (_focusedViewEnterKeyEventHandler != null)
539             {
540                 _focusedViewEnterKeyEventHandler(this, e);
541             }
542         }
543
544         /// <summary>
545         /// Please do not use! this will be deprecated!
546         /// </summary>
547         /// Please do not use! this will be deprecated!
548         /// Instead please use OnFocusedViewEnterKey.
549         [Obsolete("Please do not use! This will be deprecated! Please use FocusManager.OnFocusedViewEnterKey instead!")]
550         [EditorBrowsable(EditorBrowsableState.Never)]
551         private void OnFocusedViewEnterKey2(IntPtr view)
552         {
553             FocusedViewActivatedEventArgs e = new FocusedViewActivatedEventArgs();
554
555             e.View = Registry.GetManagedBaseHandleFromNativePtr(view) as View;
556
557             if (_focusedViewEnterKeyEventHandler != null)
558             {
559                 _focusedViewEnterKeyEventHandler(this, e);
560             }
561         }
562
563         ///<summary>
564         /// Event arguments that passed via the PreFocusChange signal.
565         /// </summary>
566         /// <since_tizen> 3 </since_tizen>
567         public class PreFocusChangeEventArgs : EventArgs
568         {
569             private View _current;
570             private View _proposed;
571             private View.FocusDirection _direction;
572
573             /// <summary>
574             /// The current focus view.
575             /// </summary>
576             /// <since_tizen> 3 </since_tizen>
577             public View CurrentView
578             {
579                 get
580                 {
581                     return _current;
582                 }
583                 set
584                 {
585                     _current = value;
586                 }
587             }
588
589             /// <summary>
590             /// The  proposed view.
591             /// </summary>
592             /// <since_tizen> 3 </since_tizen>
593             public View ProposedView
594             {
595                 get
596                 {
597                     return _proposed;
598                 }
599                 set
600                 {
601                     _proposed = value;
602                 }
603             }
604
605             /// <summary>
606             /// The focus move direction.
607             /// </summary>
608             /// <since_tizen> 3 </since_tizen>
609             public View.FocusDirection Direction
610             {
611                 get
612                 {
613                     return _direction;
614                 }
615                 set
616                 {
617                     _direction = value;
618                 }
619             }
620         }
621
622         ///<summary>
623         /// Event arguments that passed via the FocusChanged signal.
624         /// </summary>
625         /// <since_tizen> 3 </since_tizen>
626         public class FocusChangedEventArgs : EventArgs
627         {
628             private View _current;
629             private View _next;
630
631             /// <summary>
632             /// The current focus view.
633             /// </summary>
634             /// <since_tizen> 3 </since_tizen>
635             public View CurrentView
636             {
637                 get
638                 {
639                     return _current;
640                 }
641                 set
642                 {
643                     _current = value;
644                 }
645             }
646             /// <summary>
647             /// The next focus view.
648             /// </summary>
649             /// <since_tizen> 3 </since_tizen>
650             public View NextView
651             {
652                 get
653                 {
654                     return _next;
655                 }
656                 set
657                 {
658                     _next = value;
659                 }
660             }
661         }
662
663         ///<summary>
664         /// Event arguments that passed via the FocusGroupChanged signal.
665         /// </summary>
666         /// <since_tizen> 3 </since_tizen>
667         public class FocusGroupChangedEventArgs : EventArgs
668         {
669             private View _current;
670             private bool _forwardDirection;
671
672             /// <summary>
673             /// The current focus view.
674             /// </summary>
675             /// <since_tizen> 3 </since_tizen>
676             public View CurrentView
677             {
678                 get
679                 {
680                     return _current;
681                 }
682                 set
683                 {
684                     _current = value;
685                 }
686             }
687
688             /// <summary>
689             /// The forward direction.
690             /// </summary>
691             /// <since_tizen> 3 </since_tizen>
692             public bool ForwardDirection
693             {
694                 get
695                 {
696                     return _forwardDirection;
697                 }
698                 set
699                 {
700                     _forwardDirection = value;
701                 }
702             }
703         }
704
705         ///<summary>
706         /// Event arguments that passed via the FocusedViewEnterKey signal.
707         /// </summary>
708         /// <since_tizen> 3 </since_tizen>
709         public class FocusedViewActivatedEventArgs : EventArgs
710         {
711             private View _view;
712
713             /// <summary>
714             /// View.
715             /// </summary>
716             /// <since_tizen> 3 </since_tizen>
717             public View View
718             {
719                 get
720                 {
721                     return _view;
722                 }
723                 set
724                 {
725                     _view = value;
726                 }
727             }
728         }
729
730         /// <summary>
731         /// Please do not use! this will be deprecated
732         /// </summary>
733         /// <since_tizen> 3 </since_tizen>
734         /// Please do not use! this will be deprecated.
735         /// Instead please use FocusedViewActivatedEventArgs.
736         [Obsolete("Please do not use! This will be deprecated! Please use FocusedViewActivatedEventArgs instead! " +
737             "Like: " +
738             "FocusManager.Instance.FocusedViewActivated = OnFocusedViewActivated; " +
739             "private void OnFocusedViewActivated(object source, FocusManager.FocusedViewActivatedEventArgs arg)" +
740             "{...}")]
741         [EditorBrowsable(EditorBrowsableState.Never)]
742         [System.Diagnostics.CodeAnalysis.SuppressMessage("Microsoft.Design", "CA1034:NestedTypesShouldNotBeVisible")]
743         public class FocusedViewEnterKeyEventArgs : EventArgs
744         {
745             private View _view;
746
747             /// <summary>
748             /// View.
749             /// </summary>
750             /// <since_tizen> 3 </since_tizen>
751             public View View
752             {
753                 get
754                 {
755                     return _view;
756                 }
757                 set
758                 {
759                     _view = value;
760                 }
761             }
762         }
763
764         private class CustomAlgorithmInterfaceWrapper : CustomAlgorithmInterface
765         {
766             private FocusManager.ICustomFocusAlgorithm _customFocusAlgorithm;
767
768             public CustomAlgorithmInterfaceWrapper()
769             {
770             }
771
772             public void SetFocusAlgorithm(FocusManager.ICustomFocusAlgorithm customFocusAlgorithm)
773             {
774                 _customFocusAlgorithm = customFocusAlgorithm;
775             }
776
777             public override View GetNextFocusableView(View current, View proposed, View.FocusDirection direction)
778             {
779                 if (_customFocusAlgorithm == null)
780                 {
781                     Tizen.Log.Error("NUI", $"[ERROR] User defined ICustomFocusAlgorithm interface class becomes unreachable. Null will be proposed for next focusing!");
782                     return null;
783                 }
784                 return _customFocusAlgorithm.GetNextFocusableView(current, proposed, direction);
785             }
786         }
787
788
789     }
790 }