2014-03-01 33 views
2

我有一个文本框样式的按钮来清除文本框的值,
但是当事件点击按钮时,该值消失并在释放按钮鼠标时重新出现。 下面的XAML代码:如何从模板重置TextBox的TextBox文本?只有在xaml

<ResourceDictionary ..... 

<Style x:Key="SearchBoxTemplate" TargetType="{x:Type TextBox}"> 
<Setter Property="Template"> 
    <Setter.Value> 
    <ControlTemplate TargetType="{x:Type TextBox}"> 
    <Border BorderBrush="LightGray" BorderThickness="1"> 
    <StackPanel Orientation="Horizontal" > 
     <Grid Width="{TemplateBinding Width}"> 
     <Grid.ColumnDefinitions> 
      <ColumnDefinition Width="8.6*" /> 
      <ColumnDefinition Width="1.4*" /> 
     </Grid.ColumnDefinitions> 
     <TextBox Background="Transparent" x:Name="searchTextBox" Grid.Column="0" 
       HorizontalAlignment="Stretch" BorderThickness="0" 
       Text="{Binding RelativeSource={RelativeSource TemplatedParent}, Path=Text, Mode=TwoWay}" 
       Height="{TemplateBinding Height}" /> 
     <Button Background="Transparent" 
       x:Name="clearButton" Content="X" 
       Margin="2" Width="Auto" Height="Auto" 
       Grid.Column="1"/> 
     </Grid> 
    </StackPanel> 
    </Border> 
    <ControlTemplate.Triggers> 
    <Trigger SourceName="clearButton" Property="IsPressed" Value="True" > 
     <Setter TargetName="searchTextBox" Property="TextBox.Text" Value="" /> 
    </Trigger> 
    </ControlTemplate.Triggers> 
    </ControlTemplate> 
    </Setter.Value> 
</Setter> 
</Style> 

而且使用像:

<TextBox Style="{StaticResource SearchBoxTemplate}" 
      Width="200" 
      Text="{Binding SearchLastName, 
        UpdateSourceTrigger=PropertyChanged, 
        Mode=TwoWay}" /> 

// C# SearchViewModel 

internal class SearchViewModel : ViewModelBase 
{ 
private string _searchLastName; 

public string SearchLastName 
{ 
    get { return this._searchLastName; } 
    set 
    { 
     this._searchLastName = value; 
     OnPropertyChanged("SearchLastName"); 
    } 
} 
...... 

怎么了,这可能吗? 有人可以帮助我吗?

Regards

+0

您的目标是明确的绑定属性,或者你只是想改变它显示在控制的文本? – Chris

+0

两者,我想如果一个人也被删除了! 这是不正确的? – MacGile

回答

1

触发器将自动执行IsPressed =“False”的操作。编写一个侦听IsPressed =“False”的触发器。

更新答案:

<Style x:Key="SearchBoxTemplate" TargetType="{x:Type TextBox}"> 
       <Setter Property="Template"> 
        <Setter.Value> 
         <ControlTemplate TargetType="{x:Type TextBox}"> 
          <Border BorderBrush="LightGray" BorderThickness="1"> 
           <StackPanel Orientation="Horizontal" > 
            <Grid Width="{TemplateBinding Width}"> 
             <Grid.ColumnDefinitions> 
              <ColumnDefinition Width="8.6*" /> 
              <ColumnDefinition Width="1.4*" /> 
             </Grid.ColumnDefinitions> 
             <TextBox Background="Transparent" x:Name="searchTextBox" Grid.Column="0" 
       HorizontalAlignment="Stretch" BorderThickness="0" 

       Height="{TemplateBinding Height}" /> 
             <Button Background="Transparent" 
       x:Name="clearButton" Content="X" 
       Margin="2" Width="Auto" Height="Auto" 
       Grid.Column="1"/> 
            </Grid> 
           </StackPanel> 
          </Border> 
          <ControlTemplate.Triggers> 
           <Trigger SourceName="clearButton" Property="IsPressed" Value="True" > 
            <Setter TargetName="searchTextBox" Property="Text" Value="" /> 
           </Trigger> 

          </ControlTemplate.Triggers> 
         </ControlTemplate> 
        </Setter.Value> 
       </Setter> 
      </Style> 

<TextBox Style="{StaticResource SearchBoxTemplate}" 
      Width="200" 
      Text="{Binding SearchLastName,Mode=TwoWay, 
        UpdateSourceTrigger=PropertyChanged 
        }" /> 

视图模型:

internal class SearchViewModel : INotifyPropertyChanged 
    { 
     public void RaisePropertyChanged(string propertyname) 
     { 
      if (PropertyChanged != null) 
      { 
       PropertyChanged(this, new PropertyChangedEventArgs(propertyname)); 
      } 
     } 

     public event PropertyChangedEventHandler PropertyChanged; 
     private string _searchLastName=string.Empty; 

     public string SearchLastName 
     { 
      get { return _searchLastName; } 
      set 
      { 
       _searchLastName = value; 
       RaisePropertyChanged("SearchLastName"); 
      } 
     } 

    } 
+0

我试过IsPressed错误和真实,不工作。 当我输入文本框时,viewModel中的属性不会更改,并且onpropertyChanged事件不会触发。 – MacGile

+0

就好像事件没有传播一样! – MacGile

+0

你的解决方案很好地清除了文本,但是在SearchViewModel中没有更新事件激发:( 当我输入文本时,SearchLastName没有更新 当我点击清除按钮时,SearchLastName也不会更新 – MacGile

1

我不认为这是可能做到这一点在相当你atttempting(虽然我可能是错的)的方式。

我的理解是,(在按下按钮前)在一审中,你TextBox命名searchTextBox将获得从ParentTemplate指定的Path它的价值,在TextBox.Text财产 - 这势必给当地SearchLastName财产。

当你按下按钮,你覆盖已设置的searchTextBox控制,使TextBox.Text值不再从绑定PathSearchLastName获得的结合,它不是简单地设置为空字符串文字"",这是您所看到的显示内容(从您的ParentTemplateTrigger设置)。

一旦释放按钮,绑定将恢复到之前的Path到您的属性,该属性从未更改过,并且保持不变。

如果您想要清除SearchLastName属性,您必须使按钮触发一个清除搜索条件的命令/操作,或者操纵控件的属性(我相信有办法执行完全在相对绑定的用户界面中,但对于一个简单的问题它可能是一个棘手的解决方案)。我不相信你可以通过切换模板来做到这一点。

+0

是的,这似乎是发生什么:( – MacGile

0

第一个问题是您在文本框内模板上缺少UpdateSourceTrigger = PropertyChanged。 TextBox的默认值是LostFocus。您需要将其设置为PropertyChanged以防希望在textBox中输入时更新源属性。

<TextBox Background="Transparent" x:Name="searchTextBox" Grid.Column="0" 
     HorizontalAlignment="Stretch" BorderThickness="0" 
     Text="{Binding RelativeSource={RelativeSource TemplatedParent}, 
        Path=Text, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}" 
     Height="{TemplateBinding Height}" /> 

,您已经在按钮的IsPressed值使用Trigger。所以,一旦IsPressed价值逆转,它将会恢复。IsPressed状态是暂时的,您需要更新Click事件上的绑定属性,您可以通过EventTrigger来实现,但很遗憾,它不能包含setter。

因此,您应该更改Text,将其绑定到ViewModel中的ICommand,并简单地设置命令方法的基础绑定属性。

0
您的意见

最后我这样做:

在SearchviewModel

..... 
    private ICommand clearCommand; 
    public ICommand ClearCommand 
    { 
     get 
     { 
      if (this.clearCommand == null) 
       this.clearCommand = new RelayCommand(() => this.ClearSearch(),()=> CanSearch()); 

      return this.clearCommand; 
     } 
    } 

    void ClearSearch() 
    { 
     Search = string.Empty; 
    } 

    bool CanSearch() 
    { 
     return !string.IsNullOrEmpty(_search); 
    } 
    ..... 

在风格

<Style.... 
    <Button 
    .... 
    Command="{Binding ClearCommand}" /> 
</Style> 

而且我已删除触发

它的工作很好,但我想纯xaml。

非常感谢所有:)

问候

+0

但你仍然需要添加'UpdateSourceTrigger = PropertyChanged',以防你希望source属性在文本框中输入而不是lostFocus。 –

+0

我做到了,你可以在我的第一篇文章中看到:) – MacGile

+0

我意思是为模板内的textBox 'searchTextBox',不在外面的.. –