2014-11-14 3 views
2

Я использую Caliburn.micro для создания графического интерфейса для библиотеки регулярных выражений и по большей части работает. Но когда вы пытаетесь загрузить новые словари или шаблоны регулярных выражений, будет отменено необработанное исключение, и программа выйдет из строя.WPF + Caliburn.Micro: ComboBox и ListBox не обновлены со словарем правильно

В моем представлении оболочки XAML, здесь ListBox привязан к словарю, который перечисляет пары значений ключа.

<Label DockPanel.Dock="Top" > 
      <TextBlock>Selected Pattern</TextBlock> 
     </Label> 
     <TextBox Name="RegexSelectionPattern" IsReadOnly="True" cal:Message.Attach="[Event MouseDoubleClick] = [Action CopySelectedPatternToClipboard()]" DockPanel.Dock="Top" Background="White" Width="222" Height="40" Margin="0,0,4,0" ToolTip="Double click to copy to clipboard"> 
     </TextBox> 
     <Label DockPanel.Dock="Top"> 
      <TextBlock>Dictionary Selection</TextBlock> 
     </Label> 
     <ComboBox x:Name="Dictionaries" SelectedValue="{Binding ActiveRegexLibrary}" IsEditable="False" Margin="0,0,4,0" SelectedValuePath="Value" DisplayMemberPath="Key" DockPanel.Dock="Top"> 
     </ComboBox> 
     <Label DockPanel.Dock="Top"> 
      <TextBlock>Pattern Selection</TextBlock> 
     </Label> 
     <ListBox x:Name="RegexChooser" SelectedItem="{Binding RegexSelection}" Margin="0,0,4,0" SelectedValuePath="Value" DisplayMemberPath="Key" DockPanel.Dock="Top"> 
     </ListBox> 

ShellView Это дает три элемента управления в левом нижнем углу, два из которых пункт Листерс.

В ShellViewModel RegexChooser связан как словарь, который поставляется ActiveRegexLibrary. Проблема

/// <summary> 
    /// List of choosable regex patterns 
    /// </summary> 
    public Dictionary<string, string> RegexChooser 
    { 
     get 
     { 
      return this.ActiveRegexLibrary.dictionary; 
     } 
    } 

Проблемы начинают происходить, когда я использую метод для добавления большего количества шаблонов в этот словарь. (Или когда я пытаюсь добавить новые словари в ComboBox выше.) При попытке прокрутки вниз, чтобы просмотреть самую новую проблему, программа заканчивается в следующем исключении.

 Message=Information for developers (use Text Visualizer to read this): 
This exception was thrown because the generator for control 'System.Windows.Controls.ListBox Items.Count:38' with name 'RegexChooser' has received sequence of CollectionChanged events that do not agree with the current state of the Items collection. The following differences were detected: 
    Accumulated count 37 is different from actual count 38. [Accumulated count is (Count at last Reset + #Adds - #Removes since last Reset).] 

One or more of the following sources may have raised the wrong events: 
    System.Windows.Controls.ItemContainerGenerator 
     System.Windows.Controls.ItemCollection 
     MS.Internal.Data.EnumerableCollectionView 
     System.Collections.Generic.Dictionary`2[[System.String, mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089],[System.String, mscorlib, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089]] 
(The starred sources are considered more likely to be the cause of the problem.) 

The most common causes are (a) changing the collection or its Count without raising a corresponding event, and (b) raising an event with an incorrect index or item parameter. 

The exception's stack trace describes how the inconsistencies were detected, not how they occurred. To get a more timely exception, set the attached property 'PresentationTraceSources.TraceLevel' on the generator to value 'High' and rerun the scenario. One way to do this is to run a command similar to the following: 
    System.Diagnostics.PresentationTraceSources.SetTraceLevel(myItemsControl.ItemContainerGenerator, System.Diagnostics.PresentationTraceLevel.High) 
from the Immediate window. This causes the detection logic to run after every CollectionChanged event, so it will slow down the application. 

Я заметил, что способ помощи полосы фиксации этого является переключение ActiveRegexLibrary с фиктивным объектом, а затем переключить его обратно, а также ListBox отображает новый шаблон штраф. Кроме того, переключение на другой словарь в ComboBox, а затем возврат к перезагрузке ListView. Каков наилучший способ программного обновления этих списков? Ввод

NotifyOfPropertyChange(() => RegexChooser); 
NotifyOfPropertyChange(() => ActiveRegexLibrary); 

в сеттеров, как обычно делается для не список свойств в Caliburn, кажется, не работает здесь, а потому, что я использую Caliburn, я понял, что я не должен непосредственно касаться зрения с VM.

ответ

1

Я не знаю, если вы собираетесь увидеть этот ответ, но здесь я иду.

Вместо об использовании этого:

public Dictionary<string, string> RegexChooser 
{ 
    get 
    { 
     return this.ActiveRegexLibrary.dictionary; 
    } 
} 

Попробуйте использовать BindableCollection, как это:

public BindableCollection<KeyValuePair<String, String>> RegexChooser 
{ 
    get { return this.ActiveRegexLibrary.dictionary; } 
} 
Смежные вопросы