I'm not an expert in WPF so forgive me if I am wording my question weirdly. I'd be more than happy to elaborate if anything doesn't make sense.
I have a treeview that binds an observablecollection of a class. When my program launches, I read every C sourcecode files at a particular destination, store its name and filepath in the class mentioned.
Here is my XAML:
<TreeView Name="ProgramTree" ItemsSource="{Binding ProgramItemCollection}"
cal:Message.Attach="[Event PreviewMouseRightButtonDown] = [Action TestRight($dataContext,$eventArgs)];
[Event PreviewMouseDoubleClick] = [Action NodeDoubleClick($dataContext,$eventArgs)]">
<TreeView.Resources>
<!--DataTemplate for Program Nodes (Top) and binds FileItemNodes-->
<HierarchicalDataTemplate DataType="{x:Type my:ProgramItem}"
ItemsSource="{Binding FileItemCollection}">
<Border Width="100" BorderBrush="RoyalBlue"
Background="RoyalBlue" BorderThickness="1"
CornerRadius="2" Margin="2" Padding="2" >
<StackPanel Orientation="Horizontal">
<Image Style="{StaticResource IconStyle}" Margin="2" Source="{StaticResource FolderIcon}" />
<TextBlock Margin="2" Text="{Binding ProgramName}"
Foreground="White" FontWeight="Bold"/>
</StackPanel>
</Border>
</HierarchicalDataTemplate>
<!--DataTemplate for File Nodes (Subnodes of Program Nodes)-->
<HierarchicalDataTemplate DataType="{x:Type my:FileItem}">
<Border Width="80" Background="LightBlue" CornerRadius="2" Margin="1" >
<StackPanel Orientation="Horizontal">
<Image Margin="2" />
<TextBlock Margin="2" Text="{Binding NodeName}" />
</StackPanel>
</Border>
</HierarchicalDataTemplate>
</TreeView.Resources>
Codebehind:
public class FileItem
{
public string NodeName { get; set; }
public string FullName { get; set; }
public string Extension { get; set; }
}
public class ProgramItem : PropertyChangedBase
{
private ObservableCollection<FileItem> fileItemCollection;
...
What I now want to do is hook a double click event on the node and open the relevant file.
public void NodeDoubleClick(object sender, MouseButtonEventArgs e)
{
TreeViewItem treeViewItem = VisualUpwardSearch(e.OriginalSource as DependencyObject);
if (treeViewItem != null)
{
//Open file
}
}
private static TreeViewItem VisualUpwardSearch(DependencyObject source)
{
while (source != null && !(source is TreeViewItem))
source = VisualTreeHelper.GetParent(source);
return source as TreeViewItem;
}
I can retrieve the double clicked node (treeviewitem) without a problem. The problem is I want to retrieve an object of FileItem from the node I double clicked to access the filepath property. Is this possible at all?
It is possible by resolving the DataContext of the TreeViewItem:
FileItem fileItem = (treeViewItem.DataContext as FileItem);
A more elegant way would be to use MouseInput Bindings and a Command in your FileItem class.
In your Datatemplate for FileItem:
<StackPanel Orientation="Horizontal">
<StackPanel.InputBindings>
<MouseBinding MouseAction="LeftDoubleClick"
Command="{Binding OpenFileCommand}" />
</StackPanel.InputBindings>
<Image Margin="2" />
<TextBlock Margin="2" Text="{Binding NodeName}" />
</StackPanel>
In your FileItem:
public class FileItem
{
public FileItem()
{
this.OpenFileCommand
= new SimpleCommand(()=> Process.StartNew(this.FullName));
}
public string NodeName { get; set; }
public string FullName { get; set; }
public string Extension { get; set; }
public ICommand OpenFileCommand { get; set;}
}
P.S.: If you are not used to WPF's Commands, a basic implementation of a simple ICommand could be:
public class SimpleCommand : System.Windows.Input.ICommand
{
public SimpleCommand(Action action)
{
this.Action = action;
}
public Action Action { get; set; }
public bool CanExecute(object parameter)
{
return (this.Action != null);
}
public event EventHandler CanExecuteChanged;
public void Execute(object parameter)
{
if (this.Action != null)
{
this.Action();
}
}
}
Commands are much more effective for such szenarios. You dont need to walk the visual Tree and you do not need code behind at all.
Check the DataContext property of TreeViewItem and try to cast it to FileItem type.
Also you can define the template for FileItem as simple DataTemplate, not the HierarchicalDataTemplate.
Related
I have a Listbox which is bound to a DataTemplate that has another Listbox on it.
On DataTemplate there is a button that I want to use for adding items to DataTemplate ListBox, but I can't find a solution to do this.
Here is my listbox:
<Button Width="200" Content="Add Question" x:Name="btnAddQuestion" Click="btnAddQuestion_Click"/>
<StackPanel Orientation="Horizontal">
<ListBox Margin="5" x:Name="lvQuestions" ItemTemplate="{StaticResource TemplateQuestionTitle}">
</ListBox>
</StackPanel>
And this is DataTemplate:
<DataTemplate x:Key="TemplateQuestionTitle">
<StackPanel Orientation="Vertical">
<StackPanel Orientation="Horizontal">
<TextBox materialDesign:HintAssist.Hint="Enter question" MinWidth="200" Style="{StaticResource MaterialDesignFloatingHintTextBox}"/>
<Button Content="+" Command="{Binding Source={x:Reference ThisPage},Path=DataContext.Command}" />
</StackPanel>
<ListBox ItemsSource="{Binding MyItems}" MinHeight="50">
<ListBox.ItemTemplate>
<DataTemplate>
<TextBox>
</TextBox>
</DataTemplate>
</ListBox.ItemTemplate>
</ListBox>
</StackPanel>
</DataTemplate>
This is code behind on my page:
public partial class UIBuilder:Window
{
private CommandVm _commandVm;
public UIBuilder()
{
InitializeComponent();
_commandVm = new CommandVm();
DataContext = _commandVm;
}
private void btnAddQuestion_Click(object sender, RoutedEventArgs e)
{
lvQuestions.Items.Add(null);
}
}
I have implemented this code on my ViewModel in order to add items to datatemplate ListBox:
public class CommandVm
{
public ObservableCollection<TextBox> MyItems { get; set; }
public CommandVm()
{
MyItems = new ObservableCollection<TextBox>();
Command = new RelayCommand<TextBox>(Execute);
}
private void Execute(TextBox textBox)
{
MyItems .Add(textBox);
}
public ICommand Command { get; set; }
}
I use to catch the Execute() function on button "+" click command, but my code doesn't add any ListBox item.
MyItems is a property of the parent view model which means that you should bind to it like this:
<ListBox ItemsSource="{Binding DataContext.MyItems,
RelativeSource={RelativeSource AncestorType=Window}}" MinHeight="50">
This also means that you are using one single collection of items for all questions. Besides this obvious design flaw, a view model should not contain any TextBox elements. This basically breaks what the MVVM pattern is all about.
What you should do to make this example MVVM compliant is to create a Question class that has a collection of items, e.g.:
public class Question
{
public Question()
{
AddAnswerCommand = new RelayCommand<object>(Execute);
}
private void Execute(object obj)
{
Items.Add(new Answer());
}
public ObservableCollection<Answer> Items { get; }
= new ObservableCollection<Answer>();
public ICommand AddAnswerCommand { get; }
}
public class Answer { }
The window's view model should then have a collection of questions:
public class CommandVm
{
public CommandVm()
{
AddQuestionCommand = new RelayCommand<object>(Execute);
}
public ObservableCollection<Question> Questions { get; }
= new ObservableCollection<Question>();
public ICommand AddQuestionCommand { get; }
private void Execute(object obj)
{
Questions.Add(new Question());
}
}
The view and the bindings could then be defined like this:
<Window.Resources>
<DataTemplate x:Key="TemplateQuestionTitle">
<StackPanel Orientation="Vertical">
<StackPanel Orientation="Horizontal">
<TextBox MinWidth="200" />
<Button Content="+" Command="{Binding AddAnswerCommand}" />
</StackPanel>
<ListBox ItemsSource="{Binding Items}" MinHeight="50">
<ListBox.ItemTemplate>
<DataTemplate>
<TextBox />
</DataTemplate>
</ListBox.ItemTemplate>
</ListBox>
</StackPanel>
</DataTemplate>
</Window.Resources>
<StackPanel>
<Button Width="200" Content="Add Question" Command="{Binding AddQuestionCommand}"/>
<ListBox Margin="5"
ItemsSource="{Binding Questions}"
ItemTemplate="{StaticResource TemplateQuestionTitle}" />
</StackPanel>
This setup lets you add individual elements to each separate question.
I have created a treeview in my xaml.
<TreeView Name="exportTreeView" ItemsSource="{Binding}" Width="350" >
<TreeView.Resources>
<DataTemplate x:Key="layersTemplate">
<StackPanel Orientation="Horizontal" Margin="10,0,0,0">
<CheckBox Foreground="White" IsChecked="{Binding IsToBeExported}" VerticalAlignment="Center" />
<Label Style="{StaticResource baseStyle}" Content="{Binding Path=Name}" VerticalAlignment="Center" />
</StackPanel>
</DataTemplate>
<HierarchicalDataTemplate x:Key="objectTemplate" ItemsSource="{Binding Path=LayersList}" ItemTemplate="{StaticResource ResourceKey=layersTemplate}">
<StackPanel Orientation="Horizontal" Height="15" Margin="10,0,0,0">
<CheckBox Foreground="White" IsChecked="{Binding IsToBeExported}" VerticalAlignment="Center" />
<Label Style="{StaticResource baseStyle}" Content="{Binding Path=Name}" VerticalAlignment="Center" />
</StackPanel>
</HierarchicalDataTemplate>
</TreeView.Resources>
<TreeView.ItemTemplate>
<HierarchicalDataTemplate ItemsSource="{Binding Path=ObjectList}" ItemTemplate="{StaticResource ResourceKey=objectTemplate}">
<StackPanel Orientation="Horizontal" Margin="10,0,0,0">
<CheckBox Foreground="White" IsChecked="{Binding IsToBeExported}" VerticalAlignment="Center" />
<Label Style="{StaticResource baseStyle}" Content="{Binding Path=Name}" VerticalAlignment="Center" />
</StackPanel>
</HierarchicalDataTemplate>
</TreeView.ItemTemplate>
The tree structure is like below. Each Parent can have any number of children & each Child can have any number of Grandchildren. Multiple selection is allowed too.
Parent
-Child
--Grandchild
I have checkboxes for all levels. I am not getting how to access its nodes individually and also how to use the tree data.
In my VM class, I set the datacontext of this TreeView to a 3 class list like below:
public class MProject
{
public string Name { get; set; }
public bool IsToBeExported { get; set; }
public List<MWorkObject> ObjectList { get; set; }
}
public class MWorkObject
{
public string Name { get; set; }
public bool IsToBeExported { get; set; }
public List<MLayer> LayersList { get; set; }
}
public class MLayer
{
public string Name { get; set; }
public bool IsToBeExported { get; set; }
}
My requirement is:
Selecting the parent should select all its child and grandchild.
How to identify in the code which item is selected ? Need it to do further processing.
Please help.
You need to implement INotifyPropertyChanged for your classes. Then
in setter of IsToBeExported in MProject handle all children (set
IsToBeExported to what you need). The binding makes the change
visible in tree
if IsToBeExported set to true, then it is selected
Example:
public class ViewBase :INotifyPropertyChanged
{
public event PropertyChangedEventHandler PropertyChanged;
protected void NotifyPropertyChanged(string info)
{
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(info));
}
}
public class MProject : ViewBase
{
public string Name
{
get
{
return _name;
}
set
{
if (value != _name)
{
_name = value;
NotifyPropertyChanged(nameof(Name));
}
}
}
private string _name;
...
}
I am having truble accessing ObservableCollection (which is my ItemsSource) from command attached to each of the items.
I am trying make two list, one with all the objects and the second one with objects picked by user.
Here is my view model.
class ViewModel : VMBase
{
private ObservableCollection<Card> _cardsCollection;
public ObservableCollection<Card> CardsCollection
{
get { return _cardsCollection; }
set { _cardsCollection = value; }
}
static private ObservableCollection<Card> _pickedCards;
static public ObservableCollection<Card> PickedCards
{
get { return _pickedCards; }
set { _pickedCards = value;
NotifyPropertyChanged("PickedCards");
}
}
}
class Card : VMBase
{
public string Name { get; set; }
public Card(string name, int cost, CardType type, CardRarity rarity)
{
this.Name = name;
this.BackgroundImage = String.Format("/Images/Cards/{0}.png", name);
this.PickCardCommand = new MvvmCommand();
this.PickCardCommand.CanExecuteFunc = obj => true;
this.PickCardCommand.ExecuteFunction = PickCard;
}
public MvvmCommand PickCardCommand { get; set; }
public void PickCard(object parameter)
{
PickedCards.Add(currentCard);
//Above Does not work, not accessible
CreateDeckModel.PickedCards.Add(currentCard);
//Above does work but only if Collection is static
//but if collection is static I am unable to call NotifyPropertyChanged()
}
}
Here is my XAML file with binding
<GridView Grid.Row="1" ItemsSource="{Binding CardsCollection, Mode=TwoWay}">
<GridView.ItemTemplate>
<DataTemplate>
<Grid>
<Button Height="258" Width="180" Content="{Binding}" Margin="0,0,0,0"
Command="{Binding PickCardCommand}" CommandParameter="{Binding}">
<Button.Template>
<ControlTemplate>
<StackPanel Orientation="Vertical">
<Border BorderThickness="2" BorderBrush="White" Height="258" Width="180">
<Border.Background>
<ImageBrush ImageSource="{Binding BackgroundImage}" />
</Border.Background>
</Border>
</StackPanel>
</ControlTemplate>
</Button.Template>
</Button>
</Grid>
</DataTemplate>
</GridView.ItemTemplate>
</GridView>
Here is my MvvmCommand Class
class MvvmCommand : ICommand
{
public Predicate<object> CanExecuteFunc { get; set; }
public Action<object> ExecuteFunction { get; set; }
public void Execute(object parameter)
{
ExecuteFunction(parameter);
}
public event EventHandler CanExecuteChanged;
public bool CanExecute(object parameter)
{
return CanExecuteFunc(parameter);
}
}
}
Is there a way to access ItemsSource from Item or DataContext alternatively make command accessible for ViewModel Class?
You can point the Command to your ViewModel class by changing the button in your xaml file to the following:
<Button Height="258" Width="180" Content="{Binding}" Margin="0,0,0,0" Command="{Binding DataContext.PickCardCommand,RelativeSource={RelativeSource FindAncestor,AncestorType={x:Type vw:ViewClass}}}" CommandParameter="{Binding}">
In the RelativeSource binding you will need to change the following:
vw is the namespace for your View, this will have to be declared with the other namespaces in your xaml file.
ViewClass is the name of your class.
Then you obviously need to move the Command over to the ViewModel class from your Card class.
Windows Phone
<GridView x:Name="myGridView" Grid.Row="1" ItemsSource="{Binding CardsCollection, Mode=TwoWay}">
<GridView.ItemTemplate>
<DataTemplate>
<Grid>
<Button Height="258" Width="180" Content="{Binding}" Margin="0,0,0,0"
Command="{Binding ElementName=myGridView,
Path=DataContext.PickCardCommand}" CommandParameter="{Binding}">
<Button.Template>
<ControlTemplate>
<StackPanel Orientation="Vertical">
<Border BorderThickness="2" BorderBrush="White" Height="258" Width="180">
<Border.Background>
<ImageBrush ImageSource="{Binding BackgroundImage}" />
</Border.Background>
</Border>
</StackPanel>
</ControlTemplate>
</Button.Template>
</Button>
</Grid>
</DataTemplate>
</GridView.ItemTemplate>
</GridView>
You will see that I have now named the GridView and then used the name of the GridView in the binding as the ElementName. I believe this should work.
You can just pass the Add method of PickedCards to the Card when you create it:
class Card : VMBase
{
private readonly Action<Card> _addCard;
public Card(..., Action<Card> addCard)
{
...
_addCard = addCard;
this.PickCardCommand = new MvvmCommand();
this.PickCardCommand.CanExecuteFunc = obj => true;
this.PickCardCommand.ExecuteFunction = PickCard;
}
public MvvmCommand PickCardCommand { get; set; }
public void PickCard(object parameter)
{
_addCard(this);
}
}
Then when you create the card:
var card = new Card(..., ..., ..., ..., PickedCards.Add)
You can bind your collection to the Command parameter. Command parameter is currently bound to Item DataSource and not collection
CommandParameter="{Binding}"
Instead use RelativeBinding and bind to itemSource of grid
I have the following requirements:
Window will show a ListView with multiple items.
User should be able to check (Checkbox) any item.
a) If one item, all items should be unchecked and disabled.
b) If checked item is unchecked, than all items should be enabled.
As of now, I have the following incomplete code.
MainWindow XAML:
<Window x:Class="WpfApplication4.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="MainWindow" Height="520.149" Width="732.463">
<Window.Resources>
<ResourceDictionary Source="MainWindowResource.xaml" />
</Window.Resources>
<Grid>
<ListView x:Name="myListBox" ItemTemplate="{StaticResource OfferingTemplate}">
<ListView.ItemsPanel>
<ItemsPanelTemplate>
<UniformGrid Columns="3" VerticalAlignment="Top"/>
</ItemsPanelTemplate>
</ListView.ItemsPanel>
</ListView>
</Grid>
</Window>
DataTemplete for ListView:
<DataTemplate x:Key="OfferingTemplate">
<StackPanel>
<Grid IsEnabled="{Binding IsEnabled}">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="8"></ColumnDefinition>
<ColumnDefinition Width="120"></ColumnDefinition>
</Grid.ColumnDefinitions>
<Grid.RowDefinitions>
<RowDefinition Height="40"></RowDefinition>
<RowDefinition Height="50"></RowDefinition>
<RowDefinition Height="30"></RowDefinition>
</Grid.RowDefinitions>
<Rectangle Grid.Column="0" Grid.RowSpan="3" Fill="#F4CA16" />
<Label
Grid.Column="1"
Grid.Row="0"
Content="{Binding Title}"
FontSize="18" FontWeight="Bold"
Margin="0,0,0,0" />
<TextBlock
Grid.Column="1"
Grid.Row="1"
FontSize="10"
Text="{Binding Description}"
Foreground="Black"
TextWrapping="WrapWithOverflow"
Margin="5,0,0,0" />
<CheckBox
Grid.Column="1"
Grid.Row="2"
FontSize="14"
IsChecked="{Binding IsSelected}"
VerticalAlignment="Bottom"
Margin="5,0,0,0">
<TextBlock Text="Select" Margin="0,-2,0,0"/>
</CheckBox>
</Grid>
</StackPanel>
</DataTemplate>
Model:
class MyModel
{
public string Title { get; set; }
public string Description { get; set; }
public bool IsSelected { get; set; }
public bool IsEnabled { get; set; }
}
ViewModel:
class MyViewModel : INotifyPropertyChanged
{
private MyModel offering;
public MyViewModel()
{
offering = new MyModel();
}
public int ID { get; set; }
public string Title
{
get { return offering.Title; }
set
{
offering.Title = value;
RaisePropertyChanged("Title");
}
}
public string Description
{
get { return offering.Description; }
set
{
offering.Description = value;
RaisePropertyChanged("Description");
}
}
public bool IsSelected
{
get { return offering.IsSelected; }
set
{
offering.IsSelected = value;
RaisePropertyChanged("IsSelected");
}
}
public bool IsEnabled
{
get { return offering.IsEnabled; }
set
{
offering.IsEnabled = value;
RaisePropertyChanged("IsEnabled");
}
}
public event PropertyChangedEventHandler PropertyChanged;
private void RaisePropertyChanged(string propertyName)
{
var handler = PropertyChanged;
if (handler != null)
{
handler(this, new PropertyChangedEventArgs(propertyName));
}
}
}
This is an interesting question. Since the action you want applies to all items in the list, this logic should in list class level. Your MyViewModel class is fine. You need add some logic in your list class and XAML but thanks to Prism, it is quite easy.
The list class (not shown in your post) Contains:
public ObservableCollection<MyViewModel> MyItems { get; set; } //Binding to ItemsSource
private ICommand _selectCommand;
public ICommand SelectCommand
{
get { return _selectCommand ?? (_selectCommand = new DelegateCommand<MyViewModel>(DoSelect)); }
}
private void DoSelect(MyViewModel myViewModel)
{
foreach(var item in MyItems)
if (item != myViewModel)
{
item.IsSelected = false;
item.IsEnabled = false;
}
}
private ICommand _unselectCommand;
public ICommand UnselectCommand
{
get { return _unselectCommand ?? (_unselectCommand = new DelegateCommand<MyViewModel>(DoUnselect)); }
}
private void DoUnselect(MyViewModel myViewModel)
{
foreach (var item in MyItems)
if (item != myViewModel)
{
item.IsEnabled = true;
}
}
There are two commands, one for selecting and the other for unselecting. The magic is on XAML:
<ListView ItemsSource="{Binding Path=MyItems}" x:Name="listView">
<ListView.ItemTemplate>
<DataTemplate>
<CheckBox IsChecked="{Binding Path=IsSelected}" IsEnabled="{Binding Path=IsEnabled}">
<i:Interaction.Triggers>
<i:EventTrigger EventName="Checked">
<i:InvokeCommandAction Command="{Binding ElementName=listView, Path=DataContext.SelectCommand}"
CommandParameter="{Binding}"/>
</i:EventTrigger>
<i:EventTrigger EventName="Unchecked">
<i:InvokeCommandAction Command="{Binding ElementName=listView, Path=DataContext.UnselectCommand}"
CommandParameter="{Binding}"/>
</i:EventTrigger>
</i:Interaction.Triggers>
</CheckBox>
</DataTemplate>
</ListView.ItemTemplate>
</ListView>
Using Prism's triggers, you can map CheckBox's Checked and Unchecked event to your list view model's commands and passing the item view model as parameter.
It is working perfectly but one thing is annoying, that setting item's IsSelected is separate. When you check a CheckBox, the item behind is set to true through DataBinding but all others are set through parent view model. If your post is all your requirement, you can remove IsChecked binding and put the logic of setting one IsSelected inside list view model, which looks clenaer and easier to write test code.
I want to Bind a String element in a List to a Textbox. When i click an element the Text gets updated. But when the element in the List changes the Textbox Text doesn't change..
My Code looks like this:
XAML:
<TextBlock Foreground="White" Name="xTitel" Text="{Binding Titel}" Width="200" FontSize="36" FontWeight="Bold"/>
OnClick Function:
foreach (Channel c in App.Connector.ChannelList)
{
if (c.StationName == StationName)
{
Binding b = new Binding();
b.Source = c.CurrentTitle;
xTitel.SetBinding(TextBlock.TextProperty, b);
}
}
Channel Definition:
public class GlobalVariables : INotifyPropertyChanged
{
public static MediaElement mediaElement;
private ObservableCollection<Channel> channelList;
public ObservableCollection<Channel> ChannelList
{
get { return channelList; }
set
{
channelList = value;
NotifyPropertyChanged("ChannelList");
}
}
public event PropertyChangedEventHandler PropertyChanged;
private void NotifyPropertyChanged(String propertyName)
{
PropertyChangedEventHandler handler = PropertyChanged;
if (null != handler)
{
handler(this, new PropertyChangedEventArgs(propertyName));
}
}
}
EDIT:
What i forgot to say:
In my XAML i have a GridView where it works with Channellist Binding. If I am correct the Textbox should update everytime when my Gridview Updates. This is my Gridview:
<local:VariableGridView
IsSwipeEnabled="True"
Background="Transparent"
x:Name="itemGridView"
Margin="0,0,0,-3"
Padding="116,0,40,46"
SelectionMode="None"
IsItemClickEnabled="True"
ItemClick="ItemView_ItemClick"
Grid.RowSpan="2"
>
<local:VariableGridView.ItemsPanel>
<ItemsPanelTemplate>
<VariableSizedWrapGrid Background="Transparent" Orientation="Vertical" ItemWidth="120" ItemHeight="120"/>
</ItemsPanelTemplate>
</local:VariableGridView.ItemsPanel>
<local:VariableGridView.ItemTemplate>
<DataTemplate>
<Grid Background="{Binding Background}">
<StackPanel Orientation="Horizontal" Margin="10,0,0,0">
<Image x:Name="CurrentCover" Source="{Binding CurrentCover}" Width="90" Height="90"/>
<StackPanel Orientation="Vertical" HorizontalAlignment="Left" Margin="10,25,10,10">
<TextBlock Foreground="White" Text="{Binding Name}" Width="200" FontSize="24" FontWeight="Bold"/>
<TextBlock Foreground="White" Text="{Binding CurrentArtist}" Width="200" FontSize="12" FontWeight="Bold" />
<TextBlock Foreground="White" Text="{Binding CurrentTitle}" Width="200" FontSize="12" />
</StackPanel>
</StackPanel>
</Grid>
</DataTemplate>
</local:VariableGridView.ItemTemplate>
</local:VariableGridView>
And the Channel class:
public class Channel : INotifyPropertyChanged
{
public int Width { get; set; }
public int Height { get; set; }
public string Logo { get; set; }
public string StationName { get; set; }
public string Color { get; set; }
public SolidColorBrush Background { get; set; }
//public string Name { get; set; }
private string name;
public string Name
{
get { return name; }
set
{
name = value;
NotifyPropertyChanged("Name");
}
}
//..... More Code ...
}
(The Textboxes in this Gridview do Update. But the other textboxes, where I want to set the Binding over the Code don't update)
Should it be this?
Binding b = new Binding("CurrentTitle");
b.Source = c;
xTitel.SetBinding(TextBlock.TextProperty, b);
Edit to explain a little more: If you bind directly to the string property you will not see the changes because strings are immutable. It'll be set on the original string forever. You have to bind to the object that holds the string property and give the binding a property name (path) to watch for changes to.