Browse Source

add repro for TextPresenter.Text not getting set on initialisation.

repro/caret-binding-failure
Unknown 8 years ago
parent
commit
d07ff6a0c0
  1. 3
      samples/ControlCatalog/App.xaml
  2. 4
      samples/ControlCatalog/ControlCatalog.csproj
  3. 112
      samples/ControlCatalog/EditableTextBlock.cs
  4. 15
      samples/ControlCatalog/EditableTextBlock.xaml
  5. 40
      samples/ControlCatalog/Pages/TextBoxPage.xaml
  6. 14
      samples/ControlCatalog/Pages/TextBoxPage.xaml.cs

3
samples/ControlCatalog/App.xaml

@ -2,8 +2,9 @@
<Application.Styles>
<StyleInclude Source="resm:Avalonia.Themes.Default.DefaultTheme.xaml?assembly=Avalonia.Themes.Default"/>
<StyleInclude Source="resm:Avalonia.Themes.Default.Accents.BaseLight.xaml?assembly=Avalonia.Themes.Default"/>
<StyleInclude Source="resm:ControlCatalog.EditableTextBlock.xaml?assembly=ControlCatalog"/>
<Style Selector="TextBlock.h1">
<Style Selector="TextBlock.h1">
<Setter Property="Foreground" Value="#212121"/>
<Setter Property="FontSize" Value="20"/>
<Setter Property="FontWeight" Value="Medium"/>

4
samples/ControlCatalog/ControlCatalog.csproj

@ -22,6 +22,8 @@
<WarningLevel>4</WarningLevel>
</PropertyGroup>
<ItemGroup>
<None Remove="EditableTextBlock.cs" />
<None Remove="EditableTextBlock.xaml" />
<None Remove="Pages\ContextMenuPage.xaml" />
</ItemGroup>
<ItemGroup>
@ -29,6 +31,7 @@
<EmbeddedResource Include="App.xaml">
<SubType>Designer</SubType>
</EmbeddedResource>
<EmbeddedResource Include="EditableTextBlock.xaml" />
<EmbeddedResource Include="MainView.xaml">
<SubType>Designer</SubType>
</EmbeddedResource>
@ -89,6 +92,7 @@
<Compile Include="App.xaml.cs">
<DependentUpon>App.xaml</DependentUpon>
</Compile>
<Compile Include="EditableTextBlock.cs" />
<Compile Include="MainView.xaml.cs">
<DependentUpon>MainView.xaml</DependentUpon>
</Compile>

112
samples/ControlCatalog/EditableTextBlock.cs

@ -0,0 +1,112 @@
using Avalonia;
using Avalonia.Controls;
using Avalonia.Controls.Primitives;
using Avalonia.Data;
using Avalonia.Input;
using Avalonia.LogicalTree;
using Avalonia.Metadata;
using Avalonia.Threading;
using Avalonia.VisualTree;
using System;
namespace ControlCatalog
{
public class EditableTextBlock : TemplatedControl
{
private string _text;
private TextBox _textBox;
public static readonly DirectProperty<EditableTextBlock, string> TextProperty = TextBlock.TextProperty.AddOwner<EditableTextBlock>(
o => o.Text,
(o, v) => o.Text = v,
defaultBindingMode: BindingMode.TwoWay,
enableDataValidation: true);
[Content]
public string Text
{
get { return _text; }
set
{
SetAndRaise(TextProperty, ref _text, value);
}
}
public static readonly StyledProperty<bool> InEditModeProperty =
AvaloniaProperty.Register<EditableTextBlock, bool>(nameof(InEditMode));
public bool InEditMode
{
get { return GetValue(InEditModeProperty); }
set { SetValue(InEditModeProperty, value); }
}
protected override void OnTemplateApplied(TemplateAppliedEventArgs e)
{
base.OnTemplateApplied(e);
_textBox = e.NameScope.Find<TextBox>("PART_TextBox");
_textBox.KeyUp += _textBox_KeyUp;
}
protected override void OnDetachedFromLogicalTree(LogicalTreeAttachmentEventArgs e)
{
base.OnDetachedFromLogicalTree(e);
_textBox.KeyUp -= _textBox_KeyUp;
}
private void _textBox_KeyUp(object sender, KeyEventArgs e)
{
if (e.Key == Key.Enter || e.Key == Key.Escape)
{
ExitEditMode();
}
}
private void EnterEditMode()
{
InEditMode = true;
(VisualRoot as IInputRoot).MouseDevice.Capture(_textBox);
_textBox.CaretIndex = Text.Length - 1;
Dispatcher.UIThread.InvokeAsync(() =>
{
_textBox.Focus();
});
}
private void ExitEditMode()
{
InEditMode = false;
(VisualRoot as IInputRoot).MouseDevice.Capture(null);
}
protected override void OnPointerPressed(PointerPressedEventArgs e)
{
base.OnPointerPressed(e);
if (!InEditMode)
{
if (e.MouseButton == MouseButton.Middle)
{
EnterEditMode();
}
else if (e.ClickCount == 2)
{
EnterEditMode();
}
}
else
{
var hit = this.InputHitTest(e.GetPosition(this));
if (!this.IsVisualAncestorOf(hit))
{
ExitEditMode();
}
}
}
}
}

15
samples/ControlCatalog/EditableTextBlock.xaml

@ -0,0 +1,15 @@
<Styles xmlns="https://github.com/avaloniaui"
xmlns:cont="clr-namespace:ControlCatalog;assembly=ControlCatalog">
<Style Selector="cont|EditableTextBlock">
<Setter Property="BorderThickness" Value="0"/>
<Setter Property="Padding" Value="0"/>
<Setter Property="Template">
<ControlTemplate>
<Grid>
<TextBlock Text="{TemplateBinding Text}" IsVisible="{TemplateBinding !InEditMode}" />
<TextBox Text="{TemplateBinding Text}" IsVisible="{TemplateBinding InEditMode}" Name="PART_TextBox" Foreground="Black" />
</Grid>
</ControlTemplate>
</Setter>
</Style>
</Styles>

40
samples/ControlCatalog/Pages/TextBoxPage.xaml

@ -1,30 +1,34 @@
<UserControl xmlns="https://github.com/avaloniaui">
<StackPanel Orientation="Vertical" Gap="4">
<TextBlock Classes="h1">TextBox</TextBlock>
<TextBlock Classes="h2">A control into which the user can input text</TextBlock>
<UserControl xmlns="https://github.com/avaloniaui"
xmlns:local="clr-namespace:ControlCatalog">
<StackPanel Orientation="Vertical" Gap="4">
<TextBlock Classes="h1">TextBox</TextBlock>
<TextBlock Classes="h2">A control into which the user can input text</TextBlock>
<local:EditableTextBlock Text="{Binding TestText}" />
<TextBlock Classes="h2" Text="{Binding TestText}" />
<StackPanel Orientation="Horizontal"
<StackPanel Orientation="Horizontal"
Margin="0,16,0,0"
HorizontalAlignment="Center"
Gap="16">
<StackPanel Orientation="Vertical" Gap="8">
<TextBox Text="Lorem ipsum dolor sit amet, consectetur adipiscing elit." Width="200" />
<TextBox Width="200" Watermark="Watermark" />
<TextBox Width="200"
<StackPanel Orientation="Vertical" Gap="8">
<TextBox Text="Lorem ipsum dolor sit amet, consectetur adipiscing elit." Width="200" />
<TextBox Width="200" Watermark="Watermark" />
<TextBox Width="200"
Watermark="Floating Watermark"
UseFloatingWatermark="True"
Text="Lorem ipsum dolor sit amet, consectetur adipiscing elit."/>
<TextBox Width="200" Text="Left aligned text" TextAlignment="Left" />
<TextBox Width="200" Text="Center aligned text" TextAlignment="Center" />
<TextBox Width="200" Text="Right aligned text" TextAlignment="Right" />
</StackPanel>
<TextBox Width="200" Text="Left aligned text" TextAlignment="Left" />
<TextBox Width="200" Text="Center aligned text" TextAlignment="Center" />
<TextBox Width="200" Text="Right aligned text" TextAlignment="Right" />
</StackPanel>
<StackPanel Orientation="Vertical" Gap="8">
<TextBox AcceptsReturn="True" TextWrapping="Wrap" Width="200" Height="125"
<StackPanel Orientation="Vertical" Gap="8">
<TextBox AcceptsReturn="True" TextWrapping="Wrap" Width="200" Height="125"
Text="Multiline TextBox with TextWrapping.&#xD;&#xD;Lorem ipsum dolor sit amet, consectetur adipiscing elit. Vivamus magna. Cras in mi at felis aliquet congue. Ut a est eget ligula molestie gravida. Curabitur massa. Donec eleifend, libero at sagittis mollis, tellus est malesuada tellus, at luctus turpis elit sit amet quam. Vivamus pretium ornare est." />
<TextBox AcceptsReturn="True" Width="200" Height="125"
<TextBox AcceptsReturn="True" Width="200" Height="125"
Text="Multiline TextBox with no TextWrapping.&#xD;&#xD;Lorem ipsum dolor sit amet, consectetur adipiscing elit. Vivamus magna. Cras in mi at felis aliquet congue. Ut a est eget ligula molestie gravida. Curabitur massa. Donec eleifend, libero at sagittis mollis, tellus est malesuada tellus, at luctus turpis elit sit amet quam. Vivamus pretium ornare est." />
</StackPanel>
</StackPanel>
</StackPanel>
</StackPanel>
</StackPanel>
</UserControl>

14
samples/ControlCatalog/Pages/TextBoxPage.xaml.cs

@ -1,13 +1,27 @@
using Avalonia.Controls;
using Avalonia.Markup.Xaml;
using ReactiveUI;
namespace ControlCatalog.Pages
{
public class TestViewModel : ReactiveObject
{
private string testText = "Editable TextBlock";
public string TestText
{
get { return testText; }
set { this.RaiseAndSetIfChanged(ref testText, value); }
}
}
public class TextBoxPage : UserControl
{
public TextBoxPage()
{
this.InitializeComponent();
DataContext = new TestViewModel();
}
private void InitializeComponent()

Loading…
Cancel
Save