2010-03-17 4 views
2

컨트롤을 처음로드 할 때 TextBox의 모든 텍스트를 선택하는 가장 좋은 방법을 찾으려고합니다. MVVM 패턴을 사용하고 있으므로 TextBox의 Text 속성에 대한 양방향 바인딩을 내 ViewModel의 문자열에 사용하고 있습니다. 이 TextBox를 사용하여 이미 이름이있는 이름을 "이름을 바꿉니다". 컨트롤이로드 될 때 이전 이름을 선택하여 쉽게 삭제하고 이름을 바꿀 수 있습니다. 초기 텍스트 (이전 이름)는 내 ViewModel에서 설정하여 채워지며 데이터 바인딩이 완료된 후 TextBox에 반영됩니다.Silverlight TextBox에서 초기 텍스트 선택

내가 것 정말이 할 좋아하는이 같은 것입니다 :

<TextBox x:Name="NameTextBox" Text="{Binding NameViewModelProperty, Mode=TwoWay}" SelectedText="{Binding NameViewModelProperty, Mode=OneTime}" /> 

은 기본적으로 그냥 일회용 바인딩과 SelectedText으로 전체 텍스트를 사용합니다. 그러나 SelectedText는 DependencyProperty가 아니기 때문에 작동하지 않습니다.

내보기의 코드 숨김에 선택 코드를 추가하는 것과 완전히 다르지는 않지만이 경우 내 문제는 초기 텍스트 바인딩이 완료된 시점을 결정하는 것입니다. TextBox는 항상 빈 상태로 시작되므로 생성자에서 수행 할 수 없습니다. TextChanged 이벤트는 사용자가 새 텍스트를 입력 할 때만 발생하며 ViewModel의 초기 바인딩에서 텍스트가 변경된 경우에는 발생하지 않습니다.

모든 아이디어를 매우 높이 평가합니다.

답변

3

댄,

나는이 기능을 제공하는 매우 간단한 파생 클래스, TextBoxEx를 썼다. TextBoxEx 클래스는 TextBox에서 파생되며 모든 TextBox에 대해 XAML에서 참조 할 수 있습니다. 전화 할 방법이 없습니다. Focus 이벤트를 수신하고 텍스트 만 선택합니다. 아주 간단합니다. XAML에서

, 당신이 아래의 TextBoxEx를 구현하고, 당신이 필요한만큼 TextBoxEx 요소를 추가 어셈블리를 참조하는 다음과 같이

사용이다. 아래 예제는 데이터 바인딩을 사용하여 사용자 이름을 표시합니다.

<UserControl x:Class="MyApp.MainPage" 
    xmlns="http://schemas.microsoft.com/client/2007"  
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"  
    xmlns:c="clr-namespace:ClassLibrary;assembly=ClassLibrary" 
> 
.  
.  
.  
<c:TextBoxEx x:Name="NameTextBox" Text="{Binding NameViewModelProperty, Mode=TwoWay}" Width="120" /> 

이 코드는 아래 실버 라이트 3

using System.Windows; 
using System.Windows.Controls; 

namespace ClassLibrary 
{ 
    // This TextBox derived class selects all text when it receives focus 
    public class TextBoxEx : TextBox 
    { 
     public TextBoxEx() 
     { 
      base.GotFocus += OnGotFocus; 
     } 

     private void OnGotFocus(object sender, RoutedEventArgs e) 
     { 
      base.SelectAll(); 
     } 
    } 
} 

행운와 함께 작동합니다.

+0

내가 정말이 서브 클래 싱은 필요하다고 생각하지 않지만 SelectAll() TextBox의 GotFocus 이벤트를 호출하면 데이터 바인딩 된 텍스트조차도 원하는 것을 얻을 않았다. 하위 클래스가 될 실제 이유가 없습니다. 코드 비하인드에서이 작업을 수행했으며 더 많은 MVVMish를 얻고 싶다면 쉽게 블렌드 동작으로 리팩토링 할 수 있습니다. 감사! –

2

TextBox의 GotFocus 이벤트에서 SelectAll()을 호출하면 트릭이 나왔기 때문에 Jim의 해답을 떠날 것입니다.

실제로 TextBox를 서브 클래 싱하거나 코드 숨김으로 처리하는 대신 Blend TriggerAction과 EventTrigger를 사용하여이 작업을 수행했습니다. 비헤이비어 로직을 캡슐화 된 상태로 유지하고 XAML에서 선언적으로 기존 TextBox에 추가하는 것이 매우 간단하고 훌륭했습니다.

그냥 경우 다른 사람이 게시이 스레드를 통해 제공하고 관심 :

XAML :

<TextBox x:Name="NameTextBox" Text="{Binding NameViewModelProperty, Mode=TwoWay}"> 
    <i:Interaction.Triggers> 
     <i:EventTrigger EventName="GotFocus"> 
      <local:SelectAllAction/> 
     </i:EventTrigger> 
    </i:Interaction.Triggers> 
</TextBox> 

C#

public class SelectAllAction : TriggerAction<TextBox> 
{ 
    protected override void Invoke(object parameter) 
    { 
     if (this.AssociatedObject != null) 
     { 
      this.AssociatedObject.SelectAll(); 
     } 
    } 
} 
+0

Silverlight의 WPF 용입니까? TriggerAction을 타입으로 확장하려고 시도했을 때, 컴파일러는 TriggerAction이 일반 타입이 아니므로 타입을 받아 들일 수 없다고 불평했습니다. – Trinition

+0

이것은 Silveright 용입니다. 블렌드 트리거 및 액션을 WPF에 사용할 수 있는지 확실하지 않습니다. System.Windows.Interactivity.TriggerAction <>이 System.Windows.TriggerAction이 아니라는 것을 상속하고 있는지 확인해야합니다. Blend SDK에서 DLL을 참조해야합니다. –

1

그냥 싶어 링크 I를 추가 여기에 관한 내용은 다음과 같습니다 : fantastic discussion (의견보기) havours 대 subclassing vvs 첨부 된 속성 ...

관련 문제