0

I have a problem of visibility of the canvas in the button style. I dynamically create a stackPanel with two buttons inside for each item in a collection. The problem is that only the button of the last item appears with its canvas, the previous buttons do not anymore.

STYLE

    <!-- Delete Dictionnary -->
<ControlTemplate x:Key="PathDelete">
    <Canvas x:Name="appbar_delete" Width="76" Height="76" Clip="F1 M 0,0L 76,0L 76,76L 0,76L 0,0">
        <Path Width="27.7083" Height="35.625" Canvas.Left="24.1458" Canvas.Top="19.7917" Stretch="Fill" 
              Data="F1 M 25.3333,23.75L 50.6667,23.75C 51.5411,23.75 51.8541,27.3125 51.8541,27.3125L 24.1458,27.3125C 24.1458,27.3125 24.4589,23.75 25.3333,23.75 Z M 35.625,19.7917L 40.375,19.7917C 40.8122,19.7917 41.9583,20.9378 41.9583,21.375C 41.9583,21.8122 40.8122,22.9584 40.375,22.9584L 35.625,22.9584C 35.1878,22.9584 34.0416,21.8122 34.0416,21.375C 34.0416,20.9378 35.1878,19.7917 35.625,19.7917 Z M 27.7083,28.5L 48.2916,28.5C 49.1661,28.5 49.875,29.2089 49.875,30.0834L 48.2916,53.8334C 48.2916,54.7078 47.5828,55.4167 46.7083,55.4167L 29.2917,55.4167C 28.4172,55.4167 27.7083,54.7078 27.7083,53.8334L 26.125,30.0834C 26.125,29.2089 26.8339,28.5 27.7083,28.5 Z M 30.0833,31.6667L 30.4792,52.25L 33.25,52.25L 32.8542,31.6667L 30.0833,31.6667 Z M 36.4167,31.6667L 36.4167,52.25L 39.5833,52.25L 39.5833,31.6667L 36.4167,31.6667 Z M 43.1458,31.6667L 42.75,52.25L 45.5208,52.25L 45.9167,31.6667L 43.1458,31.6667 Z "/>
    </Canvas>
</ControlTemplate>

<!-- Button Style Dictionnary -->   
<Style x:Key="StackPanelLightButton" TargetType="{x:Type Button}">
    <Style.Resources>
        <Style TargetType="{x:Type Path}">
            <Setter Property="OverridesDefaultStyle" Value="True"/>
            <Setter Property="Fill" Value="White"/>
        </Style>
    </Style.Resources>
    <Setter Property="HorizontalContentAlignment" Value="Center"/>
    <Setter Property="VerticalContentAlignment" Value="Center"/>
    <Setter Property="SnapsToDevicePixels" Value="True"/>
    <Setter Property="Margin" Value="2,0,0,0"/>
    <Setter Property="Tag" Value=""/>
    <Setter Property="Template">
        <Setter.Value>
            <ControlTemplate TargetType="{x:Type Button}">
                <Grid Background="{x:Null}" Width="26" Height="26" SnapsToDevicePixels="True">
                    <Border Name="Border" BorderThickness="0" CornerRadius="4,0,4,0"
                            Background="Green" 
                            BorderBrush="{StaticResource BtnDatagridContentBrush}">
                        <Grid HorizontalAlignment="Center" VerticalAlignment="Center">
                            <Viewbox Stretch="Uniform">
                                <ContentPresenter x:Name="contentPresenter" Content="{TemplateBinding Content}"/>
                            </Viewbox>
                        </Grid>
                    </Border>
                    <Border Name="BorderFront" BorderThickness="0" CornerRadius="1" Panel.ZIndex="10"
                            Background="Transparent"  
                            BorderBrush="{x:Null}"/>
                </Grid>
            </ControlTemplate>
        </Setter.Value>
    </Setter>
</Style>

    <!--BntDelete-->
<Style x:Key="BtnDeleteStackPanelStyle" TargetType="{x:Type Button}" BasedOn="{StaticResource StackPanelLightButton}" x:Shared="False">
    <Setter Property="Content">
        <Setter.Value>
            <Control Template="{StaticResource PathDelete}">
                <Control.Resources>
                    <Style TargetType="{x:Type Path}" BasedOn="{StaticResource {x:Type Path}}"/>
                </Control.Resources>
            </Control>
        </Setter.Value>
    </Setter>
</Style

CREATE CODE BEHIND

    Style bntStyle = this.FindResource("BtnAlbumWrapPanelStyle") as Style;
Style bntSuppStyle = this.FindResource("BtnDeleteStackPanelStyle") as Style;
double width = Album_Panel.ActualWidth - 50;
Thickness margin = new Thickness() { Left = 10, Top = 0, Right = 0, Bottom = 0 };
Thickness marginSupp = new Thickness() { Left = 5, Top = 2, Right = 2, Bottom = 2 };
Thickness marginStack = new Thickness() { Left = 0, Top = 10, Right = 0, Bottom = 2 };

foreach (Album item in ListAlbum)
{
    StackPanel myStackPanel = new StackPanel()
    {
        Orientation = Orientation.Horizontal,
        Margin = marginStack
    };

    Button bnt = new Button()
    {
        HorizontalAlignment = HorizontalAlignment.Center,
        Width = width,
        Margin = margin,
        Style = bntStyle,
        HorizontalContentAlignment = HorizontalAlignment.Left,
        VerticalAlignment = VerticalAlignment.Center,
        Content = item.FullName,
        Tag = item,
    };
    bnt.Click += new RoutedEventHandler(btn_Click);

    Button bntSupp = new Button()
    {
        HorizontalAlignment = HorizontalAlignment.Left,
        VerticalAlignment = VerticalAlignment.Center,
        Width = 30,
        Height = 30,
        Margin = marginSupp,
        Style = bntSuppStyle,
        Visibility = Visibility.Visible,
        Tag = item,
    };
    bntSupp.Click += new RoutedEventHandler(btnSupp_Click);
    myStackPanel.Children.Add(bnt);
    myStackPanel.Children.Add(bntSupp);
    Album_Panel.Children.Add(myStackPanel);
}

Visual

would you see an error on my part?

1 Answer 1

1

this setter

<Setter Property="Content">
    <Setter.Value>
        <Control Template="{StaticResource PathDelete}">
            <Control.Resources>
                <Style TargetType="{x:Type Path}" BasedOn="{StaticResource {x:Type Path}}"/>
            </Control.Resources>
        </Control>
    </Setter.Value>
</Setter>

creates only one instance of Control, shared by all buttons. Obviously that control instance cannot be positioned in multiple places at once.

convert Control to a resource with x:Shared="False" to create multiple instances

<Control Template="{StaticResource PathDelete}" x:Key="DelContent" x:Shared="False">
    <Control.Resources>
        <Style TargetType="{x:Type Path}" BasedOn="{StaticResource {x:Type Path}}"/>
    </Control.Resources>
</Control>

and use Resource in a setter

<Style x:Key="BtnDeleteStackPanelStyle" TargetType="{x:Type Button}" BasedOn="{StaticResource StackPanelLightButton}" x:Shared="False">
    <Setter Property="Content" Value="{StaticResource DelContent}"/>
</Style

also: you can use ItemsControl to display ListAlbum collection instead of building dynamic elements in code-behind. Here is an example

Sign up to request clarification or add additional context in comments.

6 Comments

Thank you so much for the quick answer I followed your advice for ItemsControl and it works very well. In addition it does not work for 'DelContent' because the 'Path' are no longer visible for any button.I think it's a problem with 'PathDelete' Fill propoerty because if i fix his value, it's works..
@Alematt, Path inside appbar_delete doesn't have any Fill color. Set e.g. Fill="White"
Yes, but Fill="White" is given in 'StackPanelLightButton' resources Style!
And i don't want to fix Fill in 'appbar_delete' because i'll add trigger mouseover for fill.
what about named style : decalre it with key<Style TargetType="{x:Type Path}" x:Key="pathStyle">, and for Path add Style="{DynamicResource pathStyle}". then it is applied properly, without any <Style TargetType="{x:Type Path}" BasedOn="{StaticResource {x:Type Path}}"/>
|

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.