tags:

views:

359

answers:

5

Hi iam trying to access a button in a .xaml file within a code behind file of my MainWindow.xaml . I Have tried to use x:Class in the file but when i use it the button works but i get alot of other errors. so i prefer not to use this method.

Is there any other ways to access controls in a template with a frpm the mainWindows class.

hope u guys understands what i mean

the code

<ResourceDictionary xmlns='http://schemas.microsoft.com/winfx/2006/xaml/presentation'
                xmlns:x='http://schemas.microsoft.com/winfx/2006/xaml'
                xmlns:l="clr-namespace:Avalon.Demo" x:Class="Bildbanken.MainWindow">

                        <!-- Taggarnas placering under bilderna (Left/ Top/ Right/ Bottom) -->
                        <Label Content="{Binding Type}" Padding="0,5,7,0" HorizontalAlignment="Right" />
                        <Label Content="{Binding Category}" Padding="7,0,0,0" />
                        <ListBox Name="ArtInfo" ItemsSource="{Binding Articles}" BorderThickness="0" Background="{TemplateBinding Background}">
                            <ListBox.ItemTemplate>
                                <DataTemplate>
                                    <Grid>
                                        <Grid.ColumnDefinitions>
                                            <ColumnDefinition Width="115px" />
                                            <ColumnDefinition Width="auto" />
                                        </Grid.ColumnDefinitions>
                                        <TextBlock Grid.Column="0" Text="{Binding Artnr}"></TextBlock>
                                        <Button HorizontalAlignment="Right" Name="testbutton" Grid.Column="1">--</Button>
                                    </Grid>
                                </DataTemplate>
                            </ListBox.ItemTemplate>
                        </ListBox>

..... end

A: 

It is possible to access the contents of a datatemplate. You can get the root element of the template like this:

UIElement templateRoot = listbox.ItemTemplate.LoadContent() as UIElement;

From there, you use the VisualTreeHelper to look for a Button control.

If you are just looking to handle the click of the button, utilizing the RoutedEvents of WPF is a better alternative.

AddHandler(Button.ClickEvent, new RoutedEventHandler(Button_Click));

This will grab every button click, regardless of the source. If you give the button a tag or something, you can test that to filter just those buttons you want.

mdm20
A: 

Could you please specify WHY are you trying to get reference to a button in a template? I may be wrong but in 99.9% it's a bad practice to do such things in WPF. – arconaut 15 hours ago

its me Tan Luu...

The reason that i wanna do this is something like this. I have a listview of many items, In every item i wanna add a remove button. When i click on the button it removes the specific item that i want.. Is there any better way to do this // thanks for ur comment //Tan

A: 

You can specify a RoutedCommand which you can add via CommandBinding to you DataTemplate and to the button. That way you can handle the button click / command execute for example in the code behind and do not need find the button via the VisualTreeHelper (or my tipp would be SomeElement.TryFindResource("ButtonKey")).

Clear what I mean or did I missunderstand the thing you want to do with you button?

dalind
A: 

But theres no code behind the template. The code file is under MainWindow file. How can i connect this template file to the code.

A: 

First your make a .cs file, where you register your commands. This could be named MyCommandCollection.cs. In this class you define and register your RoutedCommand with:

   public static readonly RoutedCommand ButtonPressCommand= new RoutedCommand("ButtonPress", typeof(MyCommandCollection));

You define the Command in the UserControl or the Window you want to use it within e.g.

<UserControl.CommandBindings>
     <CommandBinding Command="Commands:MyCommandCollection.ButtonPressCommand" Execute="Execute_ButtonPressCommand" ... />
</UserControl.CommandBindings>

In the code-behind of your UserControl / Window you implement the Execute / CanExecute methods of your command.

That way you can use it also in an ResourceDictionary, for example like that:

<Button Command="Commands:MyCommandCollection.ButtonPressCommand" />

Don't forget to also put the namespaces of your "MyCommandCollectionClass.cs" in the UserControl / Window and the ResourceDictionary, for example:

xmlns:Commands="clr-namespace:MyApp.SomeFolder.Commands"

Hope this helps.

dalind