AvaloniaEdit 实现binding
组件:Avalonia.AvaloniaEdit
最近项目有需要用到富文本框,主要记录一下binding的使用过程
1.binding Document
View代码:
<avaloniaEdit:TextEditor
Grid.Column="0"
VerticalAlignment="Stretch"
Background="#FFEEEEEE"
Document="{Binding Model.DataMap.WriteStringText}"
SyntaxHighlighting="{x:Null}"
WordWrap="True" />
model:
public TextDocument WriteStringText { get; set; } = new TextDocument();
这种方式是通过绑定了一个TextDocument 对象,此时后续对富文本框的编辑就需要引出TextDocument.Text属性,来实现富文本框的内容刷新,实际经常使用富文本框来显示Model的string属性,此时使用操作存在一定局限性binding无法直接与document交互,不做推荐。
2. 附加属性实现binding
View:
<avaloniaEdit:TextEditor Name="reqViewText" Grid.Column="0" VerticalAlignment="Stretch" common:TextEditorHelper.IsSubscribed="True" common:TextEditorHelper.Text="{Binding Model.InterFace.SelectInterFace.Interface_ExReqData, Mode=TwoWay}" Background="#FFEEEEEE" SyntaxHighlighting="{x:Null}" WordWrap="True"> </avaloniaEdit:TextEditor>
Model:
private string _iterface_ExReqData; public string Interface_ExReqData { get { return _iterface_ExReqData; } set { _iterface_ExReqData = value; OnPropertyChanged(nameof(Interface_ExReqData)); } }
这里通过附加属性此时就可以直接binding到model的string属性上,方便快捷。
附加属性类:
public class TextEditorHelper { /// <summary> /// 定义Text附加属性 /// </summary> public static readonly AttachedProperty<string> TextProperty = AvaloniaProperty.RegisterAttached<TextEditorHelper, TextEditor, string>( "Text", default, false, BindingMode.TwoWay); /// <summary> /// 订阅状态附加属性 /// </summary> private static readonly AttachedProperty<bool> IsSubscribedProperty = AvaloniaProperty.RegisterAttached<TextEditorHelper, TextEditor, bool>( "IsSubscribed", default); private static readonly Dictionary<TextEditor, bool> _updating = new(); static TextEditorHelper() { TextProperty.Changed.AddClassHandler<TextEditor>(OnTextPropertyChanged); IsSubscribedProperty.Changed.AddClassHandler<TextEditor>(OnIsSubscribedChanged); } /// <summary> /// Text属性变更处理 /// </summary> private static void OnTextPropertyChanged(TextEditor editor, AvaloniaPropertyChangedEventArgs args) { if (_updating.TryGetValue(editor, out var isUpdating) && isUpdating) return; try { _updating[editor] = true; var newValue = args.GetNewValue<string>(); if (editor.Text != newValue) { editor.Text = newValue; } } finally { _updating[editor] = false; } } /// <summary> /// TextEditor内容变更处理 /// </summary> private static void OnTextChanged(object sender, EventArgs e) { if (sender is TextEditor editor) { if (_updating.TryGetValue(editor, out var isUpdating) && isUpdating) return; try { _updating[editor] = true; SetText(editor, editor.Text ?? string.Empty); } finally { _updating[editor] = false; } } } /// <summary> /// 订阅状态变更处理 /// </summary> private static void OnIsSubscribedChanged(TextEditor editor, AvaloniaPropertyChangedEventArgs args) { var isSubscribed = args.GetNewValue<bool>(); if (isSubscribed) { editor.TextChanged += OnTextChanged; } else { editor.TextChanged -= OnTextChanged; } } /// <summary> /// 设置Text附加属性 /// </summary> public static void SetText(TextEditor element, string value) { element.SetValue(TextProperty, value); SetIsSubscribed(element, true); // 自动启用订阅 } /// <summary> /// 获取Text附加属性 /// </summary> public static string GetText(TextEditor element) => element.GetValue(TextProperty); /// <summary> /// 获取订阅状态 /// </summary> public static bool GetIsSubscribed(TextEditor element) => element.GetValue(IsSubscribedProperty); /// <summary> /// 设置订阅状态 /// </summary> public static void SetIsSubscribed(TextEditor element, bool value) => element.SetValue(IsSubscribedProperty, value); }
其实还有第三种方法,通过Interaction.Behaviors行为,也可以binding到text上

浙公网安备 33010602011771号