Create WPF-MahApps.Metro Animated tab control to MetroWindow title bar - wpf

Can we able to create a MahApps Metro Master Animated Tab Control on to Metro Window title bar ?
I wrote a code like,
<Controls:MetroWindow.WindowCommands>
<Controls:WindowCommands HorizontalAlignment="Left">
<Grid HorizontalAlignment="Left">
<TabControl ItemsSource="{Binding Items1}" FontWeight="Thin" HorizontalAlignment="Left" HorizontalContentAlignment="Left">
<TabControl.ItemTemplate>
<DataTemplate>
<Grid>
<StackPanel Orientation="Horizontal">
<Rectangle Width="20" Height="10">
<Rectangle.Resources>
<SolidColorBrush x:Key="BlackBrush" Color="White"/>
</Rectangle.Resources>
<Rectangle.Fill>
<!--<VisualBrush Stretch="Fill" Visual="{StaticResource appbar_cupcake}" />-->
<ImageBrush Stretch="Fill" ImageSource="/Resources/Images/menu-home-off.png"></ImageBrush>
</Rectangle.Fill>
</Rectangle>
<TextBlock FontSize="14" FontWeight="Bold" Text="{Binding Name}"/>
</StackPanel>
</Grid>
</DataTemplate>
</TabControl.ItemTemplate>
<TabControl.ContentTemplate>
<DataTemplate>
<Label Margin="100 100 100 100" Content="{Binding Content}" Foreground="White" />
</DataTemplate>
</TabControl.ContentTemplate>
</TabControl>
</Grid>
</Controls:WindowCommands>
</Controls:MetroWindow.WindowCommands>
The Tab ItemTemplate is displaying in Title Window, The ContentTemplate is not displaying....
Is it possible?
If yes, How can i achieve this ?
Thanks in advance !!

Related

Get binding from listbox item label

I have a listbox in WPF which consists of few labels and a rectangle.
I am trying to get all the label values of items in a ListBox.
My WPF markup for ListBox is:
<ListBox x:Name="izabraniList" ItemTemplate="{DynamicResource izabraniIzbornik}" Margin="0,80,10,108" HorizontalAlignment="Right" Width="289" Background="{x:Null}" ScrollViewer.HorizontalScrollBarVisibility="Hidden">
<ListBox.Resources>
<DataTemplate x:Key="izabraniIzbornik">
<Border BorderBrush="white" CornerRadius="2,2,2,2" BorderThickness="1,1,1,1">
<StackPanel Orientation="Horizontal" Width="254" Height="64" UseLayoutRounding="False" Opacity="100">
<DockPanel>
<Rectangle Height="62" Width="62"
Margin="2,0" RadiusX="5" RadiusY="5" >
<Rectangle.Fill>
<ImageBrush ImageSource="{Binding Path=ART_SIFRA, Converter={StaticResource ImageSourceConverter}}"/>
</Rectangle.Fill>
</Rectangle>
</DockPanel>
<DockPanel Width="133" >
<Label Content="{Binding ART_NAZIV}"
VerticalAlignment="Center"
HorizontalAlignment="left"
FontSize="12" Width="auto" Foreground="#FF303030" FontWeight="Bold" />
</DockPanel>
<DockPanel HorizontalAlignment="right" Width="55" Height="64">
<DockPanel HorizontalAlignment="Right" VerticalAlignment="top" Height="20" FlowDirection="RightToLeft"/>
<DockPanel HorizontalAlignment="Right" VerticalAlignment="bottom" Height="64" FlowDirection="RightToLeft" Width="55">
<Label x:Name="cijena" Content="{Binding SKC_PRICE}" FontSize="11" DockPanel.Dock="Right" HorizontalAlignment="Center" VerticalAlignment="Center" FontWeight="Bold" Width="55" />
<Label Content="{Binding kolicina}" FontSize="11" DockPanel.Dock="Right" HorizontalAlignment="left" VerticalAlignment="top" FontWeight="Bold" Width="55" />
</DockPanel>
</DockPanel>
</StackPanel>
</Border>
</DataTemplate>
</ListBox.Resources>
</ListBox>
And I would like to do something like this:
For Each i As String In izabraniList.Items("SKC_PRICE")
Console.WriteLine(i)
Next
make a separate property in your class that flattens the list (i.e.
public string property { get { return String.Join(", ", izabranilist.Select(x => x.Skc_Price).toarray()); } }
and then bind that to the label.

DataTemplate only shows Canvas for the last record

I'm using the following DataTemplate
<DataTemplate x:Key="platform_resources">
<StackPanel Orientation="Horizontal">
<Viewbox Width="30" Height="30" ToolTip="Network Domain Count" Stretch="Uniform">
<ContentControl DataContext="{Binding}" Focusable="False" Content="{DynamicResource appbar_server}" />
</Viewbox>
<TextBlock Margin="0,7,0,0" Text="{Binding Path=workload_count}"/>
<Separator Style="{StaticResource {x:Static ToolBar.SeparatorStyleKey}}" />
<Viewbox Width="30" Height="30" ToolTip="Logical Network Count" Stretch="Uniform">
<ContentControl Focusable="False" Content="{DynamicResource appbar_network_server_connecting}" />
</Viewbox>
<TextBlock Margin="0,7,0,0" Text="{Binding Path=vlan_count}"/>
<Separator Style="{StaticResource {x:Static ToolBar.SeparatorStyleKey}}" />
<Viewbox Width="30" Height="30" ToolTip="Network Domain Count" Stretch="Uniform">
<ContentControl Focusable="False" Content="{DynamicResource appbar_network}" />
</Viewbox>
<TextBlock Margin="0,7,0,0" Text="{Binding Path=networkdomain_count}"/>
</StackPanel>
</DataTemplate>
The template displays all the relevant data with separators but only shows the images on the last record. It's leaves spaces where the images are supposed to be, but no images.
Make sure you add x:Shared="False" property to your resources.
Example:
<Canvas x:Key="appbar_server" x:Shared="False">
<!-- ... -->
</Canvas>
This happens because you probably defined some Images (e.g appbar_server) in your resources and trying to display them in multiple items. But Image is a Visual and in WPF each Visual can only have one parent. So when your items are being generated, each item steals the Image from the previous one until the last item finally gets it.
Solution:
Unlike Image, BitmapImage is not a Visual and thus can be set multiple times as the source of different items. So instead of defining Images in your Resources, define BitmapImages:
<Window.Resources>
<BitmapImage x:Key="appbar_server" UriSource="C:\...\appbar_server.png"/>
....
And then instead of ContentControls create Image instances in your DataTemplate to present them:
<DataTemplate>
<StackPanel Orientation="Horizontal">
<Viewbox Width="30" Height="30" ToolTip="Network Domain Count" Stretch="Uniform">
<Image Focusable="False" Source="{DynamicResource appbar_server}" />
</Viewbox>
<TextBlock Margin="0,7,0,0" Text="{Binding Path=workload_count}"/>
...
*Update:
The image is captured in a canvas which seems to be needing some
special wrapper to make this work.
In that case, you should define a DataTemplate for each Canvas like this:
<Window.Resources>
<DataTemplate x:Key="appbar_3d_3ds">
<Canvas Width="76" Height="76" Clip="F1 M 0,0L 76,0L 76,76L 0,76L 0,0">
<Path Width="32" Height="40" Canvas.Left="23" Canvas.Top="18" Stretch="Fill" Fill="Black" Data="F1 M 27,18L 23,26L 33,30L 24,38L 33,46L 23,50L 27,58L 45,58L 55,38L 45,18L 27,18 Z "/>
</Canvas>
</DataTemplate>
....
And then create ContentPresenter Instances in your ItemTemplate with their ContentTemplate set to your pre-defined data templates (e.g. appbar_3d_3ds).
<DataTemplate>
<StackPanel Orientation="Horizontal">
<Viewbox Width="30" Height="30" ToolTip="Network Domain Count" Stretch="Uniform">
<ContentPresenter ContentTemplate="{DynamicResource appbar_3d_3ds}"/>
</Viewbox>
<TextBlock Margin="0,7,0,0" Text="{Binding Path=workload_count}"/>
....

How can I wrap a custom text?

I have a listbox that uses datatemplates and one of the elements in the template is a textblock. Problem is that the words won't wrap, and I don't want to set a fixed size. Anybody that knows how to resolve this problem? It's driving me crazy!
<ListBox Grid.Row=" 1" HorizontalContentAlignment="Stretch" Background="#24221f" ItemsSource="{Binding Messages}" ScrollViewer.VerticalScrollBarVisibility="Visible" ClipToBounds="False" BorderBrush="{x:Null}">
<ListBox.ItemTemplate>
<DataTemplate >
<Border BorderBrush="#24221f" BorderThickness="3" Width=" auto">
<DockPanel Background="{StaticResource blackBackground}" HorizontalAlignment="Stretch" Width="auto">
<Border BorderThickness="3" BorderBrush="Transparent">
<Image Source="{Binding IconImageUrl}" VerticalAlignment="top" Height="22" Width ="22" DockPanel.Dock="Left" />
</Border>
<Border BorderThickness="3" BorderBrush="LightGray" Height="auto" Width="auto" HorizontalAlignment="Left" VerticalAlignment="Center" DockPanel.Dock="Left">
<Image Source="{Binding ProfileImageUrl}" VerticalAlignment="Top" HorizontalAlignment="Left" Height="48" Width ="48" />
</Border>
<StackPanel Orientation="Vertical" DockPanel.Dock="Left" Margin="5,0,0,0">
<Label Content="{Binding Path=Sender}" Foreground="#feb41c" FontFamily="Verdana" FontWeight="Bold" FontSize="14" />
<TextBlock Width="100" Text="{Binding Path=ShortMessage}" Margin="10,0,0,0" Foreground="BlanchedAlmond" TextWrapping="Wrap" FontFamily="Verdana" />
<Label Content="{Binding Path=Time}" Margin="10,0,0,0" Foreground="DarkGray" FontFamily="Verdana" FontStyle="Italic"/>
</StackPanel>
</DockPanel>
</Border>
</DataTemplate>
</ListBox.ItemTemplate>
</ListBox>
StackPanel is Evil :=) when i have strange behaviours in a xaml which include StackPanel, switching to a Grid with right parameters ( fixed sized, or stars or "Auto" ) often fix the issue.
Note also that there is an error in your xaml since you set the DockPanel.Dock of your first image (IconImageUrl) whereas it is in the border that surrrounds it that you should be setting it. That may get the Layout to do strange things.
just try with HorizontalContentAlignment property to "Stretch" of ListBoxItems using the Style
<Style TargetType="{x:Type ListBoxItem}" >
<Setter Property="HorizontalContentAlignment" Value="Stretch" />
</Style>
and also disable the HorizontalScrollBar visibility
ScrollViewer.HorizontalScrollBarVisibility="Disabled"
Update
<Window.Resources>
<SolidColorBrush x:Key="blackBackground" Color="Black"/>
<Style TargetType="{x:Type ListBoxItem}" >
<Setter Property="HorizontalContentAlignment" Value="Stretch" />
</Style>
</Window.Resources>
<Grid>
<ListBox Grid.Row=" 1" HorizontalContentAlignment="Stretch" Background="#24221f" ScrollViewer.HorizontalScrollBarVisibility="Disabled"
ItemsSource="{Binding Messages}" ScrollViewer.VerticalScrollBarVisibility="Visible" ClipToBounds="False" BorderBrush="{x:Null}">
<ListBox.ItemTemplate>
<DataTemplate >
<Border BorderBrush="#24221f" BorderThickness="3" Width=" auto">
<DockPanel Background="{StaticResource blackBackground}" HorizontalAlignment="Stretch" Width="auto">
<Border BorderThickness="3" BorderBrush="Transparent">
<Image Source="{Binding IconImageUrl}" VerticalAlignment="top" Height="22" Width ="22" DockPanel.Dock="Left" />
</Border>
<Border BorderThickness="3" BorderBrush="LightGray" Height="auto" Width="auto" HorizontalAlignment="Left" VerticalAlignment="Center" DockPanel.Dock="Left">
<Image Source="{Binding ProfileImageUrl}" VerticalAlignment="Top" HorizontalAlignment="Left" Height="48" Width ="48" />
</Border>
<StackPanel Orientation="Vertical" DockPanel.Dock="Left" Margin="5,0,0,0">
<Label Content="{Binding Path=Sender}" Foreground="#feb41c" FontFamily="Verdana" FontWeight="Bold" FontSize="14" />
<TextBlock Text="{Binding Path=ShortMessage}" Margin="10,0,0,0" Foreground="BlanchedAlmond" TextWrapping="Wrap" FontFamily="Verdana" />
<Label Content="{Binding Path=Time}" Margin="10,0,0,0" Foreground="DarkGray" FontFamily="Verdana" FontStyle="Italic"/>
</StackPanel>
</DockPanel>
</Border>
</DataTemplate>
</ListBox.ItemTemplate>
</ListBox>
</Grid>
I think this thread answer's your question, see the accespted answer by "Nash" - Force TextBlock to wrap in WPF ListBox
( and remember to upvote the answer the the linked thread if it helps you :) )

Margin and OrientationChanged wp7

I have a listbox with ~20 items.If orientation is portait the margin of the grid must be "140,25,5,0" and width of stackpanel inside 320
If orientation is landscape margin must be "350,25,5,0" and width of stackpanel is 450.How I can change it dinamically such as conversation view in WP7?
<Grid x:Name="LayoutRoot" >
<ListBox ScrollViewer.VerticalScrollBarVisibility="Disabled" x:Name="listmy">
<ListBox.ItemTemplate>
<DataTemplate>
<local:TypeMessage Content="{Binding}">
<local:TypeMessage.Me>
<DataTemplate>
<Grid HorizontalAlignment="Right" Margin="350,25,5,0">
<TextBlock HorizontalAlignment="Right" Margin="0,-25,30,0" TextWrapping="Wrap" Text="Вы" VerticalAlignment="Top"/>
<StackPanel Background="{StaticResource PhoneAccentBrush}" Width="320">
<TextBlock TextWrapping="Wrap" Foreground="{Binding read_state, Converter={StaticResource ReadConverter}}" Text="{Binding text}" Margin="5,3" />
<TextBlock Text="{Binding date_time}" TextAlignment="Right" Margin="5,0"/>
</StackPanel>
<Path Data="m 0,0 l 16,0 l 0,16 l -16,-16"
Fill="{StaticResource PhoneAccentBrush}"
HorizontalAlignment="Right" UseLayoutRounding="False" d:LayoutOverrides="VerticalAlignment, GridBox" Height="16" VerticalAlignment="Top" Margin="0,-15.167,8.757,0" RenderTransformOrigin="0.5,0.5">
<Path.RenderTransform>
<CompositeTransform Rotation="91.157"/>
</Path.RenderTransform>
</Path>
</Grid>
</DataTemplate>
</local:TypeMessage.Me>
<local:TypeMessage.You>
<DataTemplate>
<Grid Margin="5,25,30,0" >
<Path Data="m 0,0 l 0,16 l 16,0 l -16,-16"
Fill="{StaticResource PhoneAccentBrush}"
Margin="9.5,-16,0,0" UseLayoutRounding="False" Height="16" VerticalAlignment="Top" d:LayoutOverrides="VerticalAlignment" HorizontalAlignment="Left"/>
<StackPanel Background="{StaticResource PhoneAccentBrush}" Width="320">
<TextBlock TextWrapping="Wrap" Foreground="{Binding read_state,Converter={StaticResource ReadConverter}}" Text="{Binding text}" />
<TextBlock TextAlignment="Right" Text="{Binding date_time}" />
</StackPanel>
<TextBlock HorizontalAlignment="Left" Margin="28,-27,0,0" TextWrapping="Wrap" Text="{Binding author_name}" VerticalAlignment="Top"/>
</Grid>
</DataTemplate>
</local:TypeMessage.You>
</local:TypeMessage>
</DataTemplate>
</ListBox.ItemTemplate>
</ListBox>
</Grid>
You could detect the orientation change (in the OnOrientationChanged event) and adjust the margins accordingly.
In terms of working with lots of items.
If items share the same margins you could bind the values and update the VM in the event handler.
If everything has a different margin it may be appropriate to use a different template for each orientation.
Alterntively you could look to move to a more fluid layout. Without seeing what the actual design(s) should be it's not posible to say how suitable this may be though.

retrieving the content properties from data template in wpf

I have a particular template for a listbox item which contains different textblocks. After adding the items in the listbox I want to retrieve the text of a particular textblock of a particular listbox item. How can I do that?
<ListBox x:Name="listBox1" Grid.Row="0" SelectionChanged="listBox1_SelectionChanged">
<ListBox.ItemTemplate>
<DataTemplate>
<StackPanel Orientation="Horizontal" Margin="0,2,0,0">
<CheckBox Name="cbSelect" VerticalAlignment="Center" Visibility="{Binding isVisible}"/>
<StackPanel Orientation="Vertical">
<Grid HorizontalAlignment="Stretch" >
<TextBlock Name="txtTitle" VerticalAlignment="Bottom" Text="{Binding Title}" Style="{StaticResource PhoneTextExtraLargeStyle}"/>
<TextBlock Name="txtDate" Foreground="{StaticResource PhoneInverseInactiveBrush}" HorizontalAlignment="Right" VerticalAlignment="Center" Text="{Binding CreatedOn}" Margin="0,0,30,0" Style="{StaticResource PhoneTextSmallStyle}" />
<!-- <Image x:Name="lineImg" Source="/Icons/appbar.next.rest.png" HorizontalAlignment="Right" VerticalAlignment="Bottom" Width="48" Height="48"/>-->
</Grid>
<TextBlock Name="txtContent" Foreground="{StaticResource PhoneDisabledBrush}" VerticalAlignment="Bottom" Text="{Binding Content}" Style="{StaticResource PhoneTextNormalStyle}" />
<Line Stroke="{StaticResource PhoneBorderBrush}" StrokeThickness=" 2" X1="0" Y1="0" X2="{Binding ElementName=listBox1, Path=ActualWidth}" Y2="0" Margin="0,6,0,0" ></Line>
<!-- <Image x:Name="lineImg" Source="/Icons/Line.png" HorizontalAlignment="Center" Width="500" Height="2" Margin="0,15,0,0" />-->
</StackPanel>
</StackPanel>
</DataTemplate>
</ListBox.ItemTemplate>
</ListBox>
In the above code, after adding the items to the listbox, I want the text of txtTitle of a particular item. How can I get it?
You need to get a reference to the ContentPresenter of the item.
ListBoxItem myListBoxItem = (ListBoxItem)(myListBox.ItemContainerGenerator.ContainerFromItem(myListBox.Items.CurrentItem));
ContentPresenter myContentPresenter = FindVisualChild<ContentPresenter>(myListBoxItem);
DataTemplate myDataTemplate = myContentPresenter.ContentTemplate;
TextBlock myTextBlock = (TextBlock)myDataTemplate.FindName("textBlock", myContentPresenter);
The FindVisualChild method along with the full example can be found here.

Resources