Это актуальный вопрос, который я обновил, чтобы, надеюсь, он стал немного более понятным.Короче говоря, я пытаюсь выполнить передачу свойства из выбранного элемента списка в модель представления, чтобы это свойство можно было использовать в новом запросе.В приведенном ниже коде Listbox наследует привязку данных от родительского объекта.Список содержит шаблоны данных (пользовательские элементы управления), используемые для отображения подробных результатов.
Проблема, с которой я сталкиваюсь, заключается в том, что в пользовательском элементе управления есть расширитель, который при нажатии вызывает команду из ViewModel.Из того, что я вижу, объект Listbox теряет свой контекст данных, поэтому для того, чтобы команда вызывалась при расширении расширителя, я должен явно установить datacontext расширителя.Делая это, кажется, создается новая модель представления, которая сбрасывает мое привязанное свойство (SelectedItemsID) в null.
Есть ли способ передать выбранный элемент из представления в модель представления и предотвратить сброс значения в нолькогда кнопка вызывает команду из элемента шаблона списка?
Я понимаю, что и у Prism, и у MVVMLite есть обходные пути для этого, но я не знаком ни с одной из этих платформ, поэтому не знаю, насколько сложна их реализация в моем проекте.
Может ли это быть достигнуто за пределами Prism или MVVMLite?
Исходное сообщение выглядит следующим образом:
В моем проекте у меня есть usercontrol списка, который содержит пользовательский шаблон данных.
<ListBox x:Name="ResultListBox"
HorizontalAlignment="Stretch"
Background="{x:Null}"
BorderThickness="0"
HorizontalContentAlignment="Stretch"
ItemsSource="{Binding SearchResults[0].Results,
Mode=TwoWay}"
ScrollViewer.HorizontalScrollBarVisibility="Disabled"
SelectionChanged="ResultListBox_SelectionChanged">
<ListBox.ItemTemplate>
<DataTemplate>
<dts:TypeTemplateSelector Content="{Binding}" HorizontalContentAlignment="Stretch">
<!-- CFS Template -->
<dts:TypeTemplateSelector.CFSTemplate>
<DataTemplate>
<qr:srchCFS />
</DataTemplate>
</dts:TypeTemplateSelector.CFSTemplate>
<!-- Person Template -->
<dts:TypeTemplateSelector.PersonTemplate>
<DataTemplate>
<qr:srchPerson />
</DataTemplate>
</dts:TypeTemplateSelector.PersonTemplate>
<!-- removed for brevity -->
</DataTemplate>
</ListBox.ItemTemplate>
</ListBox>
SelectionChanged вызывает следующий метод из кода
private void ResultListBox_SelectionChanged(object sender, SelectionChangedEventArgs e)
{
if (((ListBox)sender).SelectedItem != null)
_ViewModel.SelectedItemID = (((ListBox)sender).SelectedItem as QueryResult).ID.ToString();
this.NotifyPropertyChanged(_ViewModel.SelectedItemID);//binds to VM
}
В ViewModel у меня есть следующее свойство
public string SelectedItemID
{
get
{
return this._SelectedItemID;
}
set
{
if (this._SelectedItemID == value)
return;
this._SelectedItemID = value;
}
}
шаблон списка содержит пользовательский макет с элементом управления Expander.Элемент управления Expander используется для отображения более подробной информации, связанной с выбранным элементом.Эти детали (коллекция) создаются путем нового вызова моего прокси.Чтобы сделать это с помощью элемента управления Expander, я использовал выражения InvokeCommandAction
<toolkit:Expander Height="auto"
Margin="0,0,-2,0"
Foreground="#FFFFC21C"
Header="View Details"
IsExpanded="False"
DataContext="{Binding Source={StaticResource SearchViewModelDataSource}}"
Style="{StaticResource DetailExpander}">
<i:Interaction.Triggers>
<i:EventTrigger EventName="Expanded">
<i:InvokeCommandAction Command="{Binding GetCfsResultCommand}" />
</i:EventTrigger>
</i:Interaction.Triggers>
В ViewModel вызываемая команда делегата GetCFSResultCommandExecute довольно проста
private void GetCfsResultCommandExecute(object parameter)
{
long IdResult;
if (long.TryParse(SelectedItemID, out IdResult))
{
this.CallForServiceResults = this._DataModel.GetCFSResults(IdResult);}
Проблема, с которой я столкнулсяпри выборе Элемента списка, происходит событие selectionloaded, и свойство SelectedItemID обновляется с правильным идентификатором из выбранного элемента.Когда я нажимаю на расширитель, команда запускается, но для свойства SelectedItemID устанавливается значение NULL.Я проследил это с помощью Silverlight-Spy, и события соответствуют тому, что вы ожидаете, когда по нажатию на расширитель элемент списка теряет фокус, расширитель (переключается) получает фокус, и есть LeftMouseDownEvent, но я не вижу ничего, что объясняет, почемусвойство устанавливается в нуль.Я добавил тот же код, который использовался в событии изменения выбора, в событие LostFocus в элементе listboxt и все еще получил тот же результат.
Буду признателен за помощь в понимании того, почему открытое свойство SelectedItemID имеет значение NULL, когда для кнопки расширения, являющейся частью элемента управления списка, установлено значение NULL.И, конечно, я ДЕЙСТВИТЕЛЬНО был бы признателен за любую помощь в изучении того, как не задавать для свойства нулевое значение и сохранять привязанный идентификатор.
Обновление Я попытался удалить ссылку на текст данных из Expander.как это было предложено, чтобы быть проблемой.Из того, что у меня есть, поскольку это элемент шаблона данных, он «выходит» из визуального дерева и теряет ссылку на текстовый элемент данных элемента управления, который наследуется от родительского объекта.Если я попытаюсь установить текст данных в коде для элемента управления, все привязки к свойствам будут потеряны.
Моя следующая попытка состояла в том, чтобы установить текст данных для элемента управления расширением в конструкторе как
private SearchViewModel _ViewModel;
public srchCFS()
{
InitializeComponent();
this.cfsExpander.DataContext = this._ViewModel;
}
Этот подход, похоже, не работает, так как InvokeCommandAction никогда не запускается.Эта команда запускается только в том случае, если в экспандере установлен контекст данных.
заранее спасибо