Ich versuche, die Caret- / Cursorposition auf das Ende des Zeichenfolgenwerts in meinem WPF-Textfeld zu setzen, wenn ich mein Fenster zum ersten Mal öffne. Ich benutze den FocusManager, um den Fokus auf mein Textfeld zu setzen, wenn mein Fenster geöffnet wird.
Nichts scheint zu funktionieren. Irgendwelche Ideen?
Beachten Sie, dass ich das MVVM-Muster verwende und nur einen Teil der XAML aus meinem Code aufgenommen habe.
<Window
FocusManager.FocusedElement="{Binding ElementName=NumberOfDigits}"
Height="400" Width="800">
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition/>
</Grid.ColumnDefinitions>
<Grid.RowDefinitions>
<RowDefinition/>
<RowDefinition/>
</Grid.RowDefinitions>
<TextBox Grid.Column="0" Grid.Row="0"
x:Name="NumberOfDigits"
IsReadOnly="{Binding Path=IsRunning, Mode=TwoWay}"
VerticalContentAlignment="Center"
Text="{Binding Path=Digits, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}"/>
<Button Grid.Column="0" Grid.Row="1"
Margin="10,0,10,0"
IsDefault="True"
Content="Start"
Command="{Binding StartCommand}"/>
</Grid>
</Window>
Sie können auch ein Verhalten erstellen, das zwar immer noch Code-Behind ist, aber den Vorteil hat, dass es wiederverwendbar ist.
Beispiel einer einfachen Verhaltensklasse unter Verwendung des Fokusereignisses des Textfelds:
class PutCursorAtEndTextBoxBehavior: Behavior<UIElement> { private TextBox _textBox; protected override void OnAttached() { base.OnAttached(); _textBox = AssociatedObject as TextBox; if (_textBox == null) { return; } _textBox.GotFocus += TextBoxGotFocus; } protected override void OnDetaching() { if (_textBox == null) { return; } _textBox.GotFocus -= TextBoxGotFocus; base.OnDetaching(); } private void TextBoxGotFocus(object sender, RoutedEventArgs routedEventArgs) { _textBox.CaretIndex = _textBox.Text.Length; } }
Dann hängen Sie in Ihrer XAML das Verhalten wie folgt an:
<TextBox x:Name="MyTextBox" Text="{Binding Value}"> <i:Interaction.Behaviors> <behaviors:PutCursorAtEndTextBoxBehavior/> </i:Interaction.Behaviors> </TextBox>
quelle
Das hat bei mir funktioniert. Ich benutze auch das MVVM-Muster. Mein Zweck für die Verwendung einer MMVM ist es jedoch, Unit-Tests zu ermöglichen und die Aktualisierung meiner Benutzeroberfläche (lose gekoppelt) zu vereinfachen. Ich sehe mich nicht als Einheit, der die Position des Cursors testet, daher macht es mir nichts aus, für diese einfache Aufgabe auf den Code dahinter zurückzugreifen.
public ExpeditingLogView() { InitializeComponent(); this.Loaded += (sender, args) => { Description.CaretIndex = Description.Text.Length; Description.ScrollToEnd(); Description.Focus(); }; }
quelle
Bei mehrzeiliger
TextBox
Einstellung reicht der Cursor nicht aus. Versuche dies:NumberOfDigits.ScrollToEnd();
quelle
Wenn in WPF die Zeile lang genug ist, ist es wichtig, auch zum Zeilenende zu scrollen. Also benutze ich die folgenden Zeilen:
text_Box.Text = text; text_Box.CaretIndex = text.Length; text_Box.ScrollToHorizontalOffset(double.MaxValue); // or you can use this - for me works also // text_Box.ScrollToHorizontalOffset(text_Box.GetRectFromCharacterIndex(openFileDialog.FileName.Length).Right);
Aber lesen Sie diese Warnung (für mich ist es in Ordnung - wahrscheinlich bereits behoben): TextBox ScrollToHorizontalOffset scrollt nicht, nachdem der Text lang genug ist
quelle
Die @ Louis-Lösung funktioniert nicht, wenn
textbox
sie für die Vorlagenbindung oder für andere Arten von verzögerten Bindungen oder verzögerten Wertzuweisungen verwendet wirdAlso wenn die
textbox
Lösung beispielsweise in einer Datagrid-Zelle als Vorlage verwendet wird, muss diese Lösung geringfügig geändert werdenund das ist das Abonnieren eines textveränderten Ereignisses
class PutCursorAtEndTextBoxBehavior : Behavior<UIElement> { private TextBox _textBox; protected override void OnAttached() { base.OnAttached(); _textBox = AssociatedObject as TextBox; if (_textBox == null) { return; } _textBox.GotFocus += TextBoxGotFocus; // to make it work with binding _textBox.TextChanged += TextBoxGotFocus; } protected override void OnDetaching() { if (_textBox == null) { return; } _textBox.GotFocus -= TextBoxGotFocus; _textBox.TextChanged -= TextBoxGotFocus; base.OnDetaching(); } private void TextBoxGotFocus(object sender, RoutedEventArgs routedEventArgs) { _textBox.CaretIndex = _textBox.Text.Length; } }
quelle
Keine der Antworten hier hat bei mir funktioniert. Ich verwende die Bindung für die TextBox und musste das Caret direkt nach dem Öffnen des Fensters verschieben. Das hat es für mich getan:
public MyWindow() { InitializeComponent(); ContentRendered += (sender, args) => { MyTextBox.CaretIndex = MyTextBox.Text.Length; MyTextBox.ScrollToEnd(); MyTextBox.Focus(); }; }
Ähnlich wie bei Ceranski. Anstatt zu Loaded hinzuzufügen, fügen wir ContentRendered hinzu.
quelle