Dimenus
Dimenus

Reputation: 61

How to implement button handlers when using UserControls?

I'm designing an application where I'll have a templated UI format that will enumerate TabItems based on the number of objects it returns from the database (< 8). In order to generate them dynamically, I created a dynamic resource that contains all of the objects within the tab UI and assigns the resource to the content property of each TabItem. Works great, however now I'm unable to figure out how to modify the UI (and implement handlers) with this setup.

I added a temporary Test TabItem within the xaml of the window, assigned the resource, but I can't modify any of the items within the window.

Should I be using something other than UserControls? These tabs will have the exact same functionality on them, just different sets of data that need to be tabbed through. The data types will be the exact same though.

Edit 3:

<Window
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
    xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
    xmlns:local="clr-namespace:<Redacted>.WPF"
    xmlns:ToggleSwitch="clr-namespace:ToggleSwitch;assembly=ToggleSwitch" x:Class="<Redacted>.WPF.MainWindow"
    mc:Ignorable="d"
    Title="<Redacted>" Height="704" Width="1203.3">
<Window.Resources>
    <UserControl x:Key="RemoteSiteUserControl">
        <Grid Background="#FFE5E5E5">
            <Grid.RowDefinitions>
                <RowDefinition Height="334*"/>
                <RowDefinition Height="257*"/>
            </Grid.RowDefinitions>
            <Grid.ColumnDefinitions>
                <ColumnDefinition Width="10*"/>
                <ColumnDefinition Width="31*"/>
            </Grid.ColumnDefinitions>
            <ListView x:Name="listViewMachines" HorizontalAlignment="Left" Height="252" Margin="10,34,0,0" VerticalAlignment="Top" Width="261">
                <ListView.View>
                    <GridView>
                        <GridViewColumn/>
                    </GridView>
                </ListView.View>
            </ListView>
            <Label x:Name="lblMachines" Content="Machines:" HorizontalAlignment="Left" Margin="10,10,0,0" VerticalAlignment="Top" Height="26" Width="122"/>
            <Label x:Name="lblNotifications" Content="Notification Queue:" Grid.Column="1" HorizontalAlignment="Left" Height="32" Margin="10,55,0,0" Grid.Row="1" VerticalAlignment="Top" Width="167"/>
            <ListView x:Name="listViewNotifications" Grid.Column="1" HorizontalAlignment="Left" Height="160" Margin="23,87,0,0" Grid.Row="1" VerticalAlignment="Top" Width="855">
                <ListView.View>
                    <GridView>
                        <GridViewColumn/>
                    </GridView>
                </ListView.View>
            </ListView>
            <Button x:Name="btnAddMachine" Content="Add" HorizontalAlignment="Left" Margin="10,300,0,0" VerticalAlignment="Top" Width="75" Click="btnAddMachine_Click"/>
            <Button x:Name="btnModifyMachine" Content="Modify" HorizontalAlignment="Left" Margin="104,300,0,0" VerticalAlignment="Top" Width="75" Click="btnModifyMachine_Click"/>
            <Button x:Name="btnDelete" Content="Delete" HorizontalAlignment="Left" Margin="196,300,0,0" VerticalAlignment="Top" Width="75" Click="btnDelete_Click"/>
            <Label x:Name="lblIpAddress" Content="Ip Address:" HorizontalAlignment="Left" Height="23" Margin="49,81,0,0" VerticalAlignment="Top" Width="62" FontSize="10.667" RenderTransformOrigin="0.784,0.435" Grid.Row="1"/>
            <Label x:Name="lblMachineName" Content="Machine Name:" HorizontalAlignment="Left" Height="23" Margin="28,25,0,0" VerticalAlignment="Top" Width="83" FontSize="10.667" RenderTransformOrigin="0.602,0.565" Grid.Row="1"/>
            <Label x:Name="lblAlias" Content="Alias:" HorizontalAlignment="Left" Height="23" Margin="77,53,0,0" VerticalAlignment="Top" Width="34" FontSize="10.667" Grid.Row="1"/>
            <TextBox x:Name="txtMachineName" HorizontalAlignment="Left" Height="23" Margin="116,25,0,0" TextWrapping="Wrap" Text="" VerticalAlignment="Top" Width="136" FontSize="10.667" FontFamily="Arial" Grid.Row="1" IsReadOnly="True" IsReadOnlyCaretVisible="True"/>
            <TextBox x:Name="txtIpAddress" HorizontalAlignment="Left" Height="23" Margin="116,81,0,0" TextWrapping="Wrap" VerticalAlignment="Top" Width="136" Grid.Row="1" IsReadOnly="True" IsReadOnlyCaretVisible="True"/>
            <TextBox x:Name="txtAlias" HorizontalAlignment="Left" Height="23" Margin="116,53,0,0" TextWrapping="Wrap" Text="" VerticalAlignment="Top" Width="136" FontSize="10.667" FontFamily="Arial" Grid.Row="1" IsReadOnly="True" IsReadOnlyCaretVisible="True"/>
            <Label x:Name="lblStatus" Content="Status:" Grid.Column="1" HorizontalAlignment="Left" Margin="23,32,0,0" VerticalAlignment="Top" Width="53" FontSize="14.667"/>
            <Ellipse Name="ellipseStatus" Grid.Column="1" Fill="Red" HorizontalAlignment="Left" Height="18" Margin="100,37,0,0" Stroke="Black" VerticalAlignment="Top" Width="18"/>
            <Label x:Name="lblPerfCounters" Content="Performance Counters:" Grid.Column="1" HorizontalAlignment="Left" Height="30" Margin="532,23,0,0" VerticalAlignment="Top" Width="161" FontSize="14.667"/>
            <ToggleSwitch:HorizontalToggleSwitch Name="togglePerfCounters" Grid.Column="1" HorizontalAlignment="Left" Margin="747,31,0,0" VerticalAlignment="Top" Height="19" Width="76"/>
            <Label x:Name="lvlServices" Content="Services:" Grid.Column="1" HorizontalAlignment="Left" Height="30" Margin="23,84,0,0" VerticalAlignment="Top" Width="74" FontSize="14.667"/>
            <ListView x:Name="listViewServices" Grid.Column="1" HorizontalAlignment="Left" Height="229" Margin="23,114,0,0" VerticalAlignment="Top" Width="409" Grid.RowSpan="2">
                <ListView.View>
                    <GridView>
                        <GridViewColumn/>
                    </GridView>
                </ListView.View>
            </ListView>
            <Button x:Name="btnDeleteServiceMonitor" Content="Delete" HorizontalAlignment="Left" Margin="357,22,0,0" VerticalAlignment="Top" Width="75" Grid.Column="1" Grid.Row="1" Click="btnDeleteServiceMonitor_Click"/>
            <Button x:Name="btnAddServiceMonitor" Content="Add" HorizontalAlignment="Left" Margin="266,22,0,0" VerticalAlignment="Top" Width="75" Grid.Column="1" Grid.Row="1" Click="btnAddServiceMonitor_Click"/>
            <TextBox x:Name="txtCpuTimer" HorizontalAlignment="Left" Height="30" Margin="687,73,0,0" TextWrapping="Wrap" Text="" VerticalAlignment="Top" Width="136" FontSize="10.667" FontFamily="Arial" IsReadOnly="True" IsReadOnlyCaretVisible="True" Grid.Column="1"/>
            <Label x:Name="lblCpuTimer" Content="Cpu Timer(sec):" Grid.Column="1" HorizontalAlignment="Left" Height="30" Margin="588,73,0,0" VerticalAlignment="Top" Width="94"/>
            <Label x:Name="lblCpuUsage" Content="Cpu Usage(%):" Grid.Column="1" HorizontalAlignment="Left" Height="30" Margin="593,114,0,0" VerticalAlignment="Top" Width="94" RenderTransformOrigin="0.734,0.4"/>
            <TextBox x:Name="txtCpuUsage" HorizontalAlignment="Left" Height="30" Margin="687,114,0,0" TextWrapping="Wrap" Text="" VerticalAlignment="Top" Width="136" FontSize="10.667" FontFamily="Arial" IsReadOnly="True" IsReadOnlyCaretVisible="True" Grid.Column="1"/>
            <Label x:Name="lblCpuPerformance" Content="CPU Performance:" Grid.Column="1" HorizontalAlignment="Left" Height="33" Margin="543,200,0,0" VerticalAlignment="Top" Width="144" FontSize="14.667"/>
            <Label x:Name="labelDescription" Content="Additional Information:" HorizontalAlignment="Left" Margin="10,109,0,0" Grid.Row="1" VerticalAlignment="Top"/>
            <TextBox x:Name="txtDescription" HorizontalAlignment="Left" Height="107" Margin="10,140,0,0" Grid.Row="1" TextWrapping="Wrap" VerticalAlignment="Top" Width="261"/>
        </Grid>
    </UserControl>
</Window.Resources>
<Grid>
    <Grid.RowDefinitions>
        <RowDefinition Height="27*"/>
        <RowDefinition Height="619*"/>
        <RowDefinition Height="27*"/>
    </Grid.RowDefinitions>
    <Menu x:Name="menu" HorizontalAlignment="Stretch" Margin="0,0,0,0" Grid.RowSpan="1" VerticalAlignment="Stretch">
        <MenuItem Header="_File" x:Name="menuFile" HorizontalAlignment="Center" Height="27" Width="28">
        </MenuItem>
        <MenuItem Header="_Edit" x:Name="menuEdit" HorizontalAlignment="Center"/>
        <MenuItem Header="_Tools" x:Name="menuTools" HorizontalAlignment="Center">
            <MenuItem Header="_Manage Remote Sites" x:Name="menuManageRemoteSItes" HorizontalAlignment="Left"/>
        </MenuItem>
        <MenuItem Header="_Windows" x:Name="menuWindows" HorizontalAlignment="Center"/>
        <MenuItem Header="_Reports" x:Name="menuReports" HorizontalAlignment="Center"/>
        <MenuItem Header="_Help" x:Name="menuHelp" HorizontalAlignment="Center"/>
    </Menu>
    <TabControl x:Name="tabControl" HorizontalAlignment="Stretch" Margin="0,0,0,0" Grid.Row="1" VerticalAlignment="Stretch" SelectionChanged="tabControl_SelectionChanged">
        <TabItem Header="Test" Content="{DynamicResource RemoteSiteUserControl}"/>
    </TabControl>
</Grid>

Upvotes: 1

Views: 106

Answers (1)

Meredith
Meredith

Reputation: 183

To solve your immediate problem within your design, I would avoid Click events, and instead uses Commands with a DataContext. You can assign the TabItem's data context to a separate C# class (a view model), and then bind to the commands within the resource.

<TabItem DataContext="{Binding MyViewModelDataContext}" />

Note that MyViewModelDataContext must be instantiated as a public property in your .xaml.cs code behind such that it can be bound.

Then you can use commands within the template since it's a binding:

<Button Command="{Binding MyCommand}" />

where the command is implemented inside MyViewModelDataContext.

Here is a helpful command overview: How to Bind a Command in WPF

I use DevExpress's MVVM framework as well, and they have a very nice command implementation.

Also: your overall XAML code has zero binding in it. Read up on binding; it will help you. Here's a nice link that intros binding for you: http://blog.scottlogic.com/2012/04/20/everything-you-wanted-to-know-about-databinding-in-wpf-silverlight-and-wp7-part-two.html

Hope that helps.

Upvotes: 1

Related Questions