2009-03-22 8 views
1

При связывании с Wpf есть способ использовать System.String funcntions без использования преобразователей?При связывании с Wpf существует ли способ использовать System.String funcntions без использования преобразователей?

<TextBlock Text="({Binding Path=Text}).Trim()"/> 

Это в основном мое желание.

+1

Я только что понял, что мое сообщение находится на C#. Вы называете Trim без круглых скобок, вы используете VB? Если это так, добавьте тег для VB, и я могу обновить свой образец. – bendewey

+0

В будущем, пожалуйста, убедитесь, что спецификации четко указаны в вопросе, а не только в заголовке. – bendewey

+0

Я буду, спасибо. Я работаю с VB и C#, но этот пост был действительно VB, поскольку только VB поддерживает вызовы методов без скобок. – Shimmy

ответ

7

Я бы использовал конвертер.

Связывание Xaml

<StackPanel> 
    <StackPanel.Resources> 
    <local:StringTrimmingConverter x:Key="trimmingConverter" /> 
    <StackPanel.Resources> 
    <TextBlock Text="{Binding Path=Text, Converter={StaticResource trimmingConverter}}" /> 
</StackPanel> 

StringTrimmingConverter.cs

using System; 
using System.Windows.Data; 

namespace WpfApplication1 
{ 
    [ValueConversion(typeof(string), typeof(string))] 
    public class StringTrimmingConverter : IValueConverter 
    { 
     #region IValueConverter Members 
     public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture) 
     { 
      return value.ToString().Trim(); 
     } 
     public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture) 
     { 
      return value; 
     } 
     #endregion 
    } 
} 

И если VB StringTrimmingConverter.vb

Imports System.Globalization 

Public Class StringTrimmingConverter 
    Implements IValueConverter 

    Public Function ConvertBack(ByVal value As Object, ByVal targetType As Type, ByVal parameter As Object, ByVal culture As CultureInfo) As Object Implements IValueConverter.ConvertBack 
     Return value.ToString().Trim 
    End Function 

    Public Function Convert(ByVal value As Object, ByVal targetType As Type, ByVal parameter As Object, ByVal culture As CultureInfo) As Object Implements IValueConverter.Convert 
     Return value 
    End Function 

End Class 
+0

Я сказал, что не хочу, чтобы у меня были конвертеры milion, поэтому я задал вопрос, я начал изучать окончательный конвертер строк, посмотрел ниже, расскажу свое мнение о поиске, особенно в отношении адресации параметров. Большое спасибо! – Shimmy

+0

Я не знаю, почему люди так боятся иметь миллион конвертеров. просто поместите их в папку и убедитесь, что их хорошо назвали. Это соответствует принципу единой ответственности (SRP). – bendewey

+0

Я не знаю, я лично ненавижу это не только, но и все мои конвертеры помещаются в конвертеры пространства имен, и все они находятся в одном файле. с сегодняшней навигацией VS У меня нет никаких проблем. в любом случае, спасибо за сообщение. – Shimmy

0

Я создал окончательный конвертер для всех функций в System.String, необходимо некоторое улучшение хотелось бы услышать от вас, надеюсь обновить его в будущем, пожалуйста, примите:

<ValueConversion(GetType(String), GetType(String))> _ 
Class StringFunctions : Implements IValueConverter 
    Public Function Convert(ByVal value As Object, ByVal targetType As System.Type, ByVal parameter As Object, ByVal culture As System.Globalization.CultureInfo) As Object Implements System.Windows.Data.IValueConverter.Convert 
     If parameter Is Nothing OrElse Not TypeOf parameter Is String OrElse String.IsNullOrEmpty(parameter) Then Return Nothing 
     Dim parameters As New List(Of String)(parameter.ToString.Split(":"c)) 
     parameter = parameters(0) 
     parameters.RemoveAt(0) 
     If String.IsNullOrEmpty(parameter) Then Return value 

     Dim method = (From m In GetType(String).GetMethods _ 
       Where m.Name = parameter _ 
       AndAlso m.GetParameters.Count = parameters.Count).FirstOrDefault 
     If method Is Nothing Then Return value 
     Return method.Invoke(value, parameters.ToArray) 
    End Function 
    Public Function ConvertBack(ByVal value As Object, ByVal targetType As System.Type, ByVal parameter As Object, ByVal culture As System.Globalization.CultureInfo) As Object Implements System.Windows.Data.IValueConverter.ConvertBack 
     Throw New NotSupportedException 
    End Function 
End Class 

ИН переплета, когда и использовать преобразователь u имеет возможность передать параметр в преобразователь (Binding.ConverterParameter) передать все ваши параметры, разделенные: (двоеточие - вы можете изменить его в параметре ограничителя String.Split), а первым параметром является имя функции, функция будет подсчитывать дополнительные параметры и попытаться передать их.
Я все еще не работал над адресацией параметров, это неглубокая функция.

Хотели бы видеть ваши улучшения и примечания.
спасибо. Shimmy

+0

Whoa! Используйте функцию кода в редакторе, чтобы форматировать свой код. Лучше всего работать, если вы вставляете код и нажимаете кнопку. –

+0

Извините, я видел его, теперь он отформатирован :) – Shimmy

+0

Я бы предложил обобщать это, чтобы вызвать метод для любого типа объекта. Нет ничего особенного в использовании String.Фактически атрибут «[ValueConversion (typeof (string), typeof (string))]« уже некорректен для разрыва вызова, поскольку он не возвращает строку! –

0

Вам понадобится конвертер, так как вы хотите преобразовать данные, к которым привязан элемент управления. Чтобы избежать написания простых преобразований простых преобразований, вы можете использовать Dynamic Language Runtime и писать выражения на вашем любимом языке сценариев DLR (например, Python, Ruby и т. Д.).

См. my blog series для примера того, как этого достичь. Part 3 конкретно рассказывает о ValueConverters.

1

Я создал окончательный конвертер для всех функций в System.String, необходимо некоторое улучшение хотелось бы услышать от вас, надеюсь обновить его в будущем, пожалуйста, примите:

VB:

<ValueConversion(GetType(String), GetType(Object))> _ 
Class StringFunctions : Implements IValueConverter 
    Public Function Convert(ByVal value As Object, ByVal targetType As System.Type, ByVal parameter As Object, ByVal culture As System.Globalization.CultureInfo) As Object Implements System.Windows.Data.IValueConverter.Convert 
     If parameter Is Nothing OrElse Not TypeOf parameter Is String OrElse String.IsNullOrEmpty(parameter) Then Return Nothing 
     Dim parameters As New List(Of String)(parameter.ToString.Split(":"c)) 
     parameter = parameters(0) 
     parameters.RemoveAt(0) 
     If String.IsNullOrEmpty(parameter) Then Return value 

     Dim method = (From m In GetType(String).GetMethods _ 
       Where m.Name = parameter _ 
       AndAlso m.GetParameters.Count = parameters.Count).FirstOrDefault 
     If method Is Nothing Then Return value 
     Return method.Invoke(value, parameters.ToArray) 
    End Function 
    Public Function ConvertBack(ByVal value As Object, ByVal targetType As System.Type, ByVal parameter As Object, ByVal culture As System.Globalization.CultureInfo) As Object Implements System.Windows.Data.IValueConverter.ConvertBack 
     Return value.ToString() 
    End Function 
End Class 

C#: -конвертированный инструментом, не полагайтесь!

[ValueConversion(typeof(string), typeof(object))] 
public class StringConverter : IValueConverter 
{ 
    #region IValueConverter Members 

    public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture) 
    { 
     if (value == null) return null; 
     value = value.ToString(); 
     if (String.IsNullOrEmpty(value as string)) return ""; 
     if (parameter == null || !parameter is string || String.IsNullOrEmpty((string)parameter)) return value; 
     List<string> parameters = new List<string>(((string)parameter).Split(':')); 
     parameter = parameters[0]; 
     parameters.RemoveAt(0); 

     var method = (from m in typeof(String).GetMethods() 
         where m.Name== parameter 
         && m.GetParameters().Count()==parameters.Count 
          select m).FirstOrDefault(); 
     if (method == null) return value; 
     return method.Invoke(value, parameters.ToArray()); 
    } 

    public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture) 
    { 
     return value; 
    } 

    #endregion 
} 

Xaml:

<TextBox Text="{Binding Path=String, Converter={StaticResource StringConverter}, ConverterParameter=Trim:Argument:AnotherArgument}" /> 

Тогда, в связывании, когда и использовать конвертер и есть возможность передать параметр в преобразователе (Binding.ConverterParameter) передают все ваши параметры, разделенные: (двоеточие - вы можете изменить его в параметре ограничителя String.Split), а первым параметром является имя функции, функция будет подсчитывать дополнительные параметры и попытаться передать их.
Я все еще не работал над адресацией параметров, это неглубокая функция.

Хотели бы видеть ваши улучшения и примечания.
спасибо. Shimmy

+0

Немного поздно, но я согласен с вашим взглядом на конвертеры. Вам не нужно писать 20 строк (более или менее), чтобы одна линейка функций могла быть передана XAML –

0

Я знаю, что это сообщение устарело, но оно все еще первое, что появляется при поиске «WPF TextBox Binding Trim».

У меня нет ответа VB, но, пожалуйста, не используйте конвертер.
Причины:

  1. Преобразователь означает, что вы должны добавить дополнительный код XAML, чтобы все ваши XAML связывания каждый раз. Всегда добавлять дополнительный код так же плохо в XAML, как и в C#/VB.
  2. Это не позволит вам ввести пробел, если у вас установлен UpdateSourceTrigger = PropertyChanged.

Использование объектно-ориентированного программирования, как предполагается, будет использоваться. Если вам нужен Trimmed TextBox, создайте дочерний элемент TextBox под названием TrimmedTextBox и используйте его. http://www.wpfsharp.com/2014/05/15/a-simple-trimmedtextbox-for-wpf/

C#

using System.Windows.Controls; 

namespace WpfSharp.UserControls 
{ 
    public class TrimmedTextBox : TextBox 
    { 
     public TrimmedTextBox() 
     { 
      LostFocus += TrimOnLostFocus; 
     } 

     void TrimOnLostFocus(object sender, System.Windows.RoutedEventArgs e) 
     { 
      var trimTextBox = sender as TrimmedTextBox; 
      if (trimTextBox != null) 
       trimTextBox.Text = trimTextBox.Text.Trim(); 
     } 
    } 
} 

VB (я использовал конвертер на моих C# код)

Imports System.Windows.Controls 

Namespace WpfSharp.UserControls 
    Public Class TrimmedTextBox 
     Inherits TextBox 
     Public Sub New() 
      AddHandler LostFocus, AddressOf TrimOnLostFocus 
     End Sub 

     Private Sub TrimOnLostFocus(sender As Object, e As System.Windows.RoutedEventArgs) 
      Dim trimTextBox = TryCast(sender, TrimmedTextBox) 
      If trimTextBox IsNot Nothing Then 
       trimTextBox.Text = trimTextBox.Text.Trim() 
      End If 
     End Sub 
    End Class 
End Namespace 

Надеется, что это помогает. Не стесняйтесь использовать этот объект, как если бы он был общедоступным.