/* * Copyright(c) 2021 Samsung Electronics Co., Ltd. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. * */ using System; using System.ComponentModel; using System.Runtime.InteropServices; namespace Tizen.NUI.BaseComponents { /// /// A control which provides a multi-line editable text editor. /// /// 3 public partial class TextEditor { private EventHandler textEditorTextChangedEventHandler; private TextChangedCallbackDelegate textEditorTextChangedCallbackDelegate; private EventHandler textEditorScrollStateChangedEventHandler; private ScrollStateChangedCallbackDelegate textEditorScrollStateChangedCallbackDelegate; private EventHandler textEditorCursorPositionChangedEventHandler; private CursorPositionChangedCallbackDelegate textEditorCursorPositionChangedCallbackDelegate; private EventHandler textEditorMaxLengthReachedEventHandler; private MaxLengthReachedCallbackDelegate textEditorMaxLengthReachedCallbackDelegate; private EventHandler textEditorAnchorClickedEventHandler; private AnchorClickedCallbackDelegate textEditorAnchorClickedCallbackDelegate; private EventHandler textEditorSelectionClearedEventHandler; private SelectionClearedCallbackDelegate textEditorSelectionClearedCallbackDelegate; private EventHandler textEditorSelectionStartedEventHandler; private SelectionStartedCallbackDelegate textEditorSelectionStartedCallbackDelegate; private EventHandler textEditorSelectionChangedEventHandler; private SelectionChangedCallbackDelegate textEditorSelectionChangedCallbackDelegate; private EventHandler textEditorInputFilteredEventHandler; private InputFilteredCallbackDelegate textEditorInputFilteredCallbackDelegate; [UnmanagedFunctionPointer(CallingConvention.StdCall)] private delegate void TextChangedCallbackDelegate(IntPtr textEditor); [UnmanagedFunctionPointer(CallingConvention.StdCall)] private delegate void ScrollStateChangedCallbackDelegate(IntPtr textEditor, ScrollState state); [UnmanagedFunctionPointer(CallingConvention.StdCall)] private delegate void CursorPositionChangedCallbackDelegate(IntPtr textEditor, uint oldPosition); [UnmanagedFunctionPointer(CallingConvention.StdCall)] private delegate void MaxLengthReachedCallbackDelegate(IntPtr textEditor); [UnmanagedFunctionPointer(CallingConvention.StdCall)] private delegate void SelectionClearedCallbackDelegate(IntPtr textEditor); [UnmanagedFunctionPointer(CallingConvention.StdCall)] private delegate void SelectionStartedCallbackDelegate(IntPtr textEditor); [UnmanagedFunctionPointer(CallingConvention.StdCall)] private delegate void AnchorClickedCallbackDelegate(IntPtr textEditor, IntPtr href, uint hrefLength); [UnmanagedFunctionPointer(CallingConvention.StdCall)] private delegate void SelectionChangedCallbackDelegate(IntPtr textEditor, uint oldStart, uint oldEnd); [UnmanagedFunctionPointer(CallingConvention.StdCall)] private delegate void InputFilteredCallbackDelegate(IntPtr textEditor, InputFilterType type); private bool invokeTextChanged = true; /// /// An event for the TextChanged signal which can be used to subscribe or unsubscribe the event handler /// provided by the user. The TextChanged signal is emitted when the text changes.
///
/// 3 public event EventHandler TextChanged { add { if (textEditorTextChangedEventHandler == null) { textEditorTextChangedCallbackDelegate = (OnTextChanged); TextChangedSignal().Connect(textEditorTextChangedCallbackDelegate); } textEditorTextChangedEventHandler += value; } remove { textEditorTextChangedEventHandler -= value; if (textEditorTextChangedEventHandler == null && TextChangedSignal().Empty() == false) { TextChangedSignal().Disconnect(textEditorTextChangedCallbackDelegate); } } } /// /// Event for the ScrollStateChanged signal which can be used to subscribe or unsubscribe the event handler /// provided by the user. The ScrollStateChanged signal is emitted when the scroll state changes.
///
/// 3 public event EventHandler ScrollStateChanged { add { if (textEditorScrollStateChangedEventHandler == null) { textEditorScrollStateChangedCallbackDelegate = OnScrollStateChanged; ScrollStateChangedSignal(this).Connect(textEditorScrollStateChangedCallbackDelegate); } textEditorScrollStateChangedEventHandler += value; } remove { textEditorScrollStateChangedEventHandler -= value; if (textEditorScrollStateChangedEventHandler == null && ScrollStateChangedSignal(this).Empty() == false) { ScrollStateChangedSignal(this).Disconnect(textEditorScrollStateChangedCallbackDelegate); } } } /// /// The CursorPositionChanged event is emitted whenever the primary cursor position changed. /// /// 9 public event EventHandler CursorPositionChanged { add { if (textEditorCursorPositionChangedEventHandler == null) { textEditorCursorPositionChangedCallbackDelegate = (OnCursorPositionChanged); CursorPositionChangedSignal().Connect(textEditorCursorPositionChangedCallbackDelegate); } textEditorCursorPositionChangedEventHandler += value; } remove { if (textEditorCursorPositionChangedEventHandler == null && CursorPositionChangedSignal().Empty() == false) { this.CursorPositionChangedSignal().Disconnect(textEditorCursorPositionChangedCallbackDelegate); } textEditorCursorPositionChangedEventHandler -= value; } } /// /// The MaxLengthReached event. /// /// This will be public opened in tizen_6.5 after ACR done. Before ACR, need to be hidden as inhouse API. [EditorBrowsable(EditorBrowsableState.Never)] public event EventHandler MaxLengthReached { add { if (textEditorMaxLengthReachedEventHandler == null) { textEditorMaxLengthReachedCallbackDelegate = (OnMaxLengthReached); MaxLengthReachedSignal().Connect(textEditorMaxLengthReachedCallbackDelegate); } textEditorMaxLengthReachedEventHandler += value; } remove { if (textEditorMaxLengthReachedEventHandler == null && MaxLengthReachedSignal().Empty() == false) { this.MaxLengthReachedSignal().Disconnect(textEditorMaxLengthReachedCallbackDelegate); } textEditorMaxLengthReachedEventHandler -= value; } } /// /// The AnchorClicked signal is emitted when the anchor is clicked. /// /// 9 public event EventHandler AnchorClicked { add { if (textEditorAnchorClickedEventHandler == null) { textEditorAnchorClickedCallbackDelegate = (OnAnchorClicked); AnchorClickedSignal().Connect(textEditorAnchorClickedCallbackDelegate); } textEditorAnchorClickedEventHandler += value; } remove { textEditorAnchorClickedEventHandler -= value; if (textEditorAnchorClickedEventHandler == null && AnchorClickedSignal().Empty() == false) { AnchorClickedSignal().Disconnect(textEditorAnchorClickedCallbackDelegate); } } } /// /// The SelectionStarted event is emitted when the selection has been started. /// /// 10 public event EventHandler SelectionStarted { add { if (textEditorSelectionStartedEventHandler == null) { textEditorSelectionStartedCallbackDelegate = (OnSelectionStarted); SelectionStartedSignal().Connect(textEditorSelectionStartedCallbackDelegate); } textEditorSelectionStartedEventHandler += value; } remove { if (textEditorSelectionStartedEventHandler == null && SelectionStartedSignal().Empty() == false) { this.SelectionStartedSignal().Disconnect(textEditorSelectionStartedCallbackDelegate); } textEditorSelectionStartedEventHandler -= value; } } /// /// The SelectionCleared signal is emitted when selection is cleared. /// /// 9 public event EventHandler SelectionCleared { add { if (textEditorSelectionClearedEventHandler == null) { textEditorSelectionClearedCallbackDelegate = (OnSelectionCleared); SelectionClearedSignal().Connect(textEditorSelectionClearedCallbackDelegate); } textEditorSelectionClearedEventHandler += value; } remove { if (textEditorSelectionClearedEventHandler == null && SelectionClearedSignal().Empty() == false) { this.SelectionClearedSignal().Disconnect(textEditorSelectionClearedCallbackDelegate); } textEditorSelectionClearedEventHandler -= value; } } /// /// The SelectionChanged event is emitted whenever the selected text is changed. /// /// 9 public event EventHandler SelectionChanged { add { if (textEditorSelectionChangedEventHandler == null) { textEditorSelectionChangedCallbackDelegate = (OnSelectionChanged); SelectionChangedSignal().Connect(textEditorSelectionChangedCallbackDelegate); } textEditorSelectionChangedEventHandler += value; } remove { if (textEditorSelectionChangedEventHandler == null && SelectionChangedSignal().Empty() == false) { this.SelectionChangedSignal().Disconnect(textEditorSelectionChangedCallbackDelegate); } textEditorSelectionChangedEventHandler -= value; } } /// /// The InputFiltered signal is emitted when the input is filtered by InputFilter.
///
/// /// See and for a detailed description.
///
/// /// The following example demonstrates how to use the InputFiltered event. /// /// editor.InputFiltered += (s, e) => /// { /// if (e.Type == InputFilterType.Accept) /// { /// // If input is filtered by InputFilter of Accept type. /// } /// else if (e.Type == InputFilterType.Reject) /// { /// // If input is filtered by InputFilter of Reject type. /// } /// }; /// /// /// 9 public event EventHandler InputFiltered { add { if (textEditorInputFilteredEventHandler == null) { textEditorInputFilteredCallbackDelegate = (OnInputFiltered); InputFilteredSignal().Connect(textEditorInputFilteredCallbackDelegate); } textEditorInputFilteredEventHandler += value; } remove { textEditorInputFilteredEventHandler -= value; if (textEditorInputFilteredEventHandler == null && InputFilteredSignal().Empty() == false) { InputFilteredSignal().Disconnect(textEditorInputFilteredCallbackDelegate); } } } internal TextEditorSignal SelectionStartedSignal() { TextEditorSignal ret = new TextEditorSignal(Interop.TextEditor.SelectionStartedSignal(SwigCPtr), false); if (NDalicPINVOKE.SWIGPendingException.Pending) throw NDalicPINVOKE.SWIGPendingException.Retrieve(); return ret; } internal TextEditorSignal SelectionClearedSignal() { TextEditorSignal ret = new TextEditorSignal(Interop.TextEditor.SelectionClearedSignal(SwigCPtr), false); if (NDalicPINVOKE.SWIGPendingException.Pending) throw NDalicPINVOKE.SWIGPendingException.Retrieve(); return ret; } internal TextEditorSignal TextChangedSignal() { TextEditorSignal ret = new TextEditorSignal(Interop.TextEditor.TextChangedSignal(SwigCPtr), false); if (NDalicPINVOKE.SWIGPendingException.Pending) throw NDalicPINVOKE.SWIGPendingException.Retrieve(); return ret; } internal ScrollStateChangedSignal ScrollStateChangedSignal(TextEditor textEditor) { ScrollStateChangedSignal ret = new ScrollStateChangedSignal(Interop.TextEditor.ScrollStateChangedSignal(TextEditor.getCPtr(textEditor)), false); if (NDalicPINVOKE.SWIGPendingException.Pending) throw NDalicPINVOKE.SWIGPendingException.Retrieve(); return ret; } internal TextEditorSignal CursorPositionChangedSignal() { TextEditorSignal ret = new TextEditorSignal(Interop.TextEditor.CursorPositionChangedSignal(SwigCPtr), false); if (NDalicPINVOKE.SWIGPendingException.Pending) throw NDalicPINVOKE.SWIGPendingException.Retrieve(); return ret; } internal TextEditorSignal MaxLengthReachedSignal() { TextEditorSignal ret = new TextEditorSignal(Interop.TextEditor.MaxLengthReachedSignal(SwigCPtr), false); if (NDalicPINVOKE.SWIGPendingException.Pending) throw NDalicPINVOKE.SWIGPendingException.Retrieve(); return ret; } internal TextEditorSignal AnchorClickedSignal() { TextEditorSignal ret = new TextEditorSignal(Interop.TextEditor.AnchorClickedSignal(SwigCPtr), false); if (NDalicPINVOKE.SWIGPendingException.Pending) throw NDalicPINVOKE.SWIGPendingException.Retrieve(); return ret; } internal TextEditorSignal SelectionChangedSignal() { TextEditorSignal ret = new TextEditorSignal(Interop.TextEditor.SelectionChangedSignal(SwigCPtr), false); if (NDalicPINVOKE.SWIGPendingException.Pending) throw NDalicPINVOKE.SWIGPendingException.Retrieve(); return ret; } internal TextEditorSignal InputFilteredSignal() { TextEditorSignal ret = new TextEditorSignal(Interop.TextEditor.InputFilteredSignal(SwigCPtr), false); if (NDalicPINVOKE.SWIGPendingException.Pending) throw NDalicPINVOKE.SWIGPendingException.Retrieve(); return ret; } private void OnTextChanged(IntPtr textEditor) { if (textEditorTextChangedEventHandler != null && invokeTextChanged) { TextChangedEventArgs e = new TextChangedEventArgs(); // Populate all members of "e" (TextChangedEventArgs) with real data e.TextEditor = Registry.GetManagedBaseHandleFromNativePtr(textEditor) as TextEditor; //here we send all data to user event handlers textEditorTextChangedEventHandler(this, e); } } private void OnSelectionStarted(IntPtr textEditor) { //no data to be sent to the user textEditorSelectionStartedEventHandler?.Invoke(this, EventArgs.Empty); } private void OnSelectionCleared(IntPtr textEditor) { //no data to be sent to the user textEditorSelectionClearedEventHandler?.Invoke(this, EventArgs.Empty); } private void OnScrollStateChanged(IntPtr textEditor, ScrollState state) { if (textEditorScrollStateChangedEventHandler != null) { ScrollStateChangedEventArgs e = new ScrollStateChangedEventArgs(); if (textEditor != global::System.IntPtr.Zero) { // Populate all members of "e" (ScrollStateChangedEventArgs) with real data e.TextEditor = Registry.GetManagedBaseHandleFromNativePtr(textEditor) as TextEditor; e.ScrollState = state; } //here we send all data to user event handlers textEditorScrollStateChangedEventHandler(this, e); } } private void OnCursorPositionChanged(IntPtr textEditor, uint oldPosition) { // no data to be sent to the user, as in NUI there is no event provide old values. textEditorCursorPositionChangedEventHandler?.Invoke(this, EventArgs.Empty); } private void OnMaxLengthReached(IntPtr textEditor) { if (textEditorMaxLengthReachedEventHandler != null) { MaxLengthReachedEventArgs e = new MaxLengthReachedEventArgs(); // Populate all members of "e" (MaxLengthReachedEventArgs) with real data e.TextEditor = Registry.GetManagedBaseHandleFromNativePtr(textEditor) as TextEditor; //here we send all data to user event handlers textEditorMaxLengthReachedEventHandler(this, e); } } private void OnAnchorClicked(IntPtr textEditor, IntPtr href, uint hrefLength) { // Note: hrefLength is useful for get the length of a const char* (href) in dali-toolkit. // But NUI can get the length of string (href), so hrefLength is not necessary in NUI. AnchorClickedEventArgs e = new AnchorClickedEventArgs(); // Populate all members of "e" (AnchorClickedEventArgs) with real data e.Href = Marshal.PtrToStringAnsi(href); //here we send all data to user event handlers textEditorAnchorClickedEventHandler?.Invoke(this, e); } private void OnSelectionChanged(IntPtr textEditor, uint oldStart, uint oldEnd) { // no data to be sent to the user, as in NUI there is no event provide old values. textEditorSelectionChangedEventHandler?.Invoke(this, EventArgs.Empty); } private void OnInputFiltered(IntPtr textEditor, InputFilterType type) { InputFilteredEventArgs e = new InputFilteredEventArgs(); // Populate all members of "e" (InputFilteredEventArgs) with real data e.Type = type; //here we send all data to user event handlers textEditorInputFilteredEventHandler?.Invoke(this, e); } /// /// Event arguments that passed via the TextChanged signal. /// /// 3 public class TextChangedEventArgs : EventArgs { private TextEditor textEditor; /// /// TextEditor - is the texteditor control which has the text contents changed. /// /// 3 public TextEditor TextEditor { get { return textEditor; } set { textEditor = value; } } } /// /// Event arguments that passed via the ScrollStateChanged signal. /// /// 3 public class ScrollStateChangedEventArgs : EventArgs { private TextEditor textEditor; private ScrollState scrollState; /// /// TextEditor - is the texteditor control which has the scroll state changed. /// /// 3 public TextEditor TextEditor { get { return textEditor; } set { textEditor = value; } } /// /// ScrollState - is the texteditor control scroll state. /// /// 3 public ScrollState ScrollState { get { return scrollState; } set { scrollState = value; } } } /// /// The MaxLengthReached event arguments. /// /// This will be public opened in tizen_6.5 after ACR done. Before ACR, need to be hidden as inhouse API. [EditorBrowsable(EditorBrowsableState.Never)] public class MaxLengthReachedEventArgs : EventArgs { private TextEditor textEditor; /// /// TextEditor. /// /// This will be public opened in tizen_6.5 after ACR done. Before ACR, need to be hidden as inhouse API. [EditorBrowsable(EditorBrowsableState.Never)] public TextEditor TextEditor { get { return textEditor; } set { textEditor = value; } } } } }