using System; using System.ComponentModel; using System.Windows; using ICSharpCode.AvalonEdit; namespace Intromat.Controls { public class SourceEditor : TextEditor, INotifyPropertyChanged { /// /// The bindable text property dependency property /// public static readonly DependencyProperty TextProperty = DependencyProperty.Register("Text", typeof(string), typeof(SourceEditor), new FrameworkPropertyMetadata { DefaultValue = default(string), BindsTwoWayByDefault = true, PropertyChangedCallback = OnDependencyPropertyChanged }); /// /// A bindable Text property /// public new string Text { get => (string)GetValue(TextProperty); set { SetValue(TextProperty, value); RaisePropertyChanged("Text"); } } public event PropertyChangedEventHandler? PropertyChanged; protected static void OnDependencyPropertyChanged(DependencyObject obj, DependencyPropertyChangedEventArgs args) { var target = (SourceEditor)obj; if (target.Document == null) return; var caretOffset = target.CaretOffset; var newValue = args.NewValue ?? ""; target.Document.Text = (string)newValue; target.CaretOffset = Math.Min(caretOffset, target.Document.Text.Length); } protected override void OnTextChanged(EventArgs e) { if (Document != null) Text = Document.Text; base.OnTextChanged(e); } /// /// Raises a property changed event /// /// The name of the property that updates public void RaisePropertyChanged(string property) { if (PropertyChanged != null) PropertyChanged(this, new PropertyChangedEventArgs(property)); } } }