Событие текстового поля перегруженного текстового поля Silverlight 4 вызывается родительским текстовым полем. - PullRequest
0 голосов
/ 27 сентября 2011

У меня есть пользовательское текстовое поле, которое я получил от http://blog.roboblob.com/2010/07/16/custom-silverlight-textbox-control-that-immediately-updates-databound-text-property-in-twoway-binding/comment-page-1/:

public class ImmediateTextBox : TextBox
{
    public ImmediateTextBox()
    {
        this.Loaded += ImmediateTextBox_Loaded;
    }

    void ImmediateTextBox_Loaded(object sender, RoutedEventArgs e)
    {            
        this.GotFocus +=  ImmediateTextBox_GotFocus;
        this.TextChanged += new TextChangedEventHandler(ImmediateTextBox_TextChanged);
    }

    void ImmediateTextBox_TextChanged(object sender, TextChangedEventArgs e)
    {
        TextBox txt = sender as TextBox;

        if (txt != null)
        {
            BindingExpression bindExp = txt.GetBindingExpression(TextBox.TextProperty);
            if (bindExp != null)
            {
                bindExp.UpdateSource();
            }//if

        }//if

    }

    void ImmediateTextBox_GotFocus(object sender, RoutedEventArgs e)
    {
        this.SelectAll();
    }
 }

В моем xaml я использую это, и оно отлично работает, за исключением случаев, когда оно вложено и родительский контейнер имеет ImmediateTextBox:

 <ItemsControl Grid.Column="1" ItemsSource="{Binding Path=LstForecast}">
<ItemsControl.ItemsPanel>
    <ItemsPanelTemplate>
        <StackPanel Orientation="Horizontal"/>
    </ItemsPanelTemplate>
</ItemsControl.ItemsPanel>
<ItemsControl.ItemTemplate>
    <DataTemplate>
        <StackPanel Orientation="Horizontal">
                    <customControls:ImmediateTextBox Padding="8" Height="36" Text="{Binding Path=DForecastQuantityShippedTotal,
                                                                                StringFormat=\{0:n0\},
                                                                                Mode=TwoWay,
                                                                                Converter={StaticResource StringToNullableDoubleConverter}}"
                                                                                 Width="70" IsEnabled="{Binding Path=IsForecastUserEditable}"/>
            <!--Weeks-->
            <ItemsControl ItemsSource="{Binding Path=LstWeeks}">
                <ItemsControl.ItemsPanel>
                    <ItemsPanelTemplate>
                        <StackPanel Orientation="Horizontal" />
                    </ItemsPanelTemplate>
                </ItemsControl.ItemsPanel>
                <ItemsControl.ItemTemplate>
                    <DataTemplate>
                        <StackPanel Orientation="Horizontal">
                                    <customControls:ImmediateTextBox Padding="8" Width="70" Height="36"
                                                                                    Text="{Binding Path=DForecastQuantityShippedTotal, StringFormat=\{0:n0\}, Mode=TwoWay, Converter={StaticResource StringToNullableDoubleConverter}}"
                                                                                    IsEnabled="{Binding Path=IsForecastUserEditable}"/>
                            <!--days data-->
                            <ItemsControl ItemsSource="{Binding Path=LstDays}">
                                <ItemsControl.ItemsPanel>
                                    <ItemsPanelTemplate>
                                        <StackPanel Orientation="Horizontal" />
                                    </ItemsPanelTemplate>
                                </ItemsControl.ItemsPanel>
                                <ItemsControl.ItemTemplate>
                                    <DataTemplate>
                                                <customControls:ImmediateTextBox Padding="8" Width="70" Height="36"
                                                                                                             Text="{Binding Path=DForecastAutoManual,
                                                                                                                            StringFormat=\{0:n0\},
                                                                                                                            Mode=TwoWay,
                                                                                                              Converter={StaticResource StringToNullableDoubleConverter}}"
                                                                                                             IsEnabled="{Binding Path=IsForecastUserEditable}"/>
                                    </DataTemplate>
                                </ItemsControl.ItemTemplate>
                            </ItemsControl>
                            <!--end days data-->
                        </StackPanel>
                    </DataTemplate>
                </ItemsControl.ItemTemplate>
            </ItemsControl>
            <!--end weeks-->
        </StackPanel>
    </DataTemplate>
</ItemsControl.ItemTemplate>

На самом низком уровне это становится действительно забавным.изменение предыдущего и иногда следующих сгенерированных текстовых полей.Если я использую autocompletebox, конечно, это работает.Проблема в том, что я хочу добавить в текстовое поле поведения для копирования / вставки / выбора всех и т. Д., Что я не могу сделать с помощью autocompletebox, так как нет метода selectedtext или selectall ().Также я заметил в RoutedEventArgs, originalsource является нулем.Я полагал, что это заставит его работать, но нет.Любая помощь?заранее спасибо.

1 Ответ

0 голосов
/ 28 сентября 2011

Хорошо, я понял это.У меня каждое текстовое поле привязано к свойствам.Когда любое из этих текстовых полей изменяется, тогда связанные свойства ViewModel обновляют друг друга.Когда это происходит, они обновляют текстовое поле, где это происходит, а не только свойство, потому что это двусторонняя привязка.Поэтому, когда происходит обновление, вызванное вводом пользователя, оно обновляется.Это не должно происходить, когда пользователь ничего не печатает в этом текстовом поле (когда текстовое поле обновляется из алгоритма.

Мое решение заключается в создании логического свойства "isUser" в ImmediateTextBox. КогдаМои переопределенные OnKeyDown или OnMouseLeftButtonPressed вызываются, я устанавливаю isUser в true. Когда текст изменяется от пользователя, вводящего или вставляющего что-то, тогда я обновляю привязку и устанавливаю isUser в false.

...