If I have a large number of series (or data points in a single pie series), the legend gets cut off. I tried to template the chart to put a ScrollViewer around the LegendPanel, but that didn't work since the XamWebChart.cs code adds the LegendPanel to its RootElement, so I get this:
XamWebChart Warning: Element is already the child of another element
This was my template (which I applied in code behind):
<ControlTemplate TargetType="igChart:XamWebChart"> <Border BorderBrush="{TemplateBinding BorderBrush}" BorderThickness="{TemplateBinding BorderThickness}"> <Grid x:Name="RootElement" Background="{TemplateBinding Background}" Margin="{TemplateBinding Padding}" > <Grid.ColumnDefinitions> <ColumnDefinition Width="*"/> <ColumnDefinition Width="Auto" MaxWidth="200"/> </Grid.ColumnDefinitions> <Grid.RowDefinitions> <RowDefinition Height="Auto"/> <RowDefinition Height="*"/> </Grid.RowDefinitions> <Grid x:Name="CaptionPanel" Grid.Row="0" Grid.ColumnSpan="2" Grid.Column="0"/> <Grid x:Name="ScenePanel" Grid.Column="0" Grid.Row="1"/> <ScrollViewer HorizontalScrollBarVisibility="Auto" VerticalScrollBarVisibility="Auto" Grid.Column="1" Grid.Row="1" > <Grid x:Name="LegendPanel" Grid.Column="1" Grid.Row="1" /> </ScrollViewer> <!--<igChart:Legend x:Name="LegendPanel" Grid.Column="1" Grid.Row="1" MaxWidth="200"/>--> </Grid> </Border></ControlTemplate>
Is there any way to get some sort of scrolling in the legend so I can see all the items in a pie series (even beyond 50 or so gets cut off depending on the control size)?
Thanks,Keith
quick and easy way would be to update the fake canvas in the control template to look like:
<local:FakeCanvas HorizontalAlignment="Left" x:Name="RootElement" Background="Beige" > <local:FakeCanvas.ItemsControl> <ListBox Height="70" Width="200" ScrollViewer.HorizontalScrollBarVisibility="Hidden" /> </local:FakeCanvas.ItemsControl> </local:FakeCanvas>
You basically need to make sure the listbox width is appropriate to the size that the labels are being truncated to.
Automatically deciding this value would be a bit more infolved, does this work for you?
-Graham
Hi Graham,
The fake canvas approach that you have suggested introduces the scrollbar successfully in my legend box and works for multiple series also. But if I disable the horizontal scrollbar and the legend item label is very long the entire legend box shifts to the extreme right of the canvas and only partial legend box is seen. In the normal case without scrollbar infragistics legend item gets truncated when the legend item label is too long. I would ideally want this behaviour to continue.
This is one of the default feature I found was failing when I tried using the fake canvas code. Can you please look into this and help me find a solution to introduce a scrollbar in legend box without loosing on any default feature provided with infragistics
Hi,
I scrolled till the end but could not see any data. I tried the following code and it worked . But there is a problem in the code. If I have multiple series then I get a scrollable legend for each series, I do not want something like that. I want all my legend items to be displayed in one scrollable legend box. Can you tell me how to achieve that?
<igChart:XamWebChart x:Name="XamWebChart1">
<igChart:XamWebChart.Series>
<igChart:Series ChartType="Column" Label="Series 1">
<igChart:Series.DataPoints>
<igChart:DataPoint Value="10" Label="point1" />
<igChart:DataPoint Value="20" Label="point2" />
<igChart:DataPoint Value="30" Label="point3" />
</igChart:Series.DataPoints>
</igChart:Series>
</igChart:XamWebChart.Series>
<igChart:XamWebChart.Legend>
<igChart:Legend>
<igChart:Legend.LegendItemStyle>
<Style TargetType="igChart:LegendItem">
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="igChart:LegendItem">
<ScrollViewer>
<StackPanel Orientation="Horizontal" >
<Rectangle Height="10" Width="10" Fill="{TemplateBinding Fill}" Margin="0,0,3,0" />
<TextBlock Text="{TemplateBinding Text}" x:Name="Text"/>
</StackPanel>
</ScrollViewer>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
</igChart:Legend.LegendItemStyle>
</igChart:Legend>
</igChart:XamWebChart.Legend>
</igChart:XamWebChart>
Here's another option you can experiment with. It creates uses a canvas control that reformats content that is added to it into a different control instead. This might get you started on other ways to rearrange the content:
The Code:
public class FakeCanvas : Canvas { public FakeCanvas() { this.LayoutUpdated += new EventHandler(FakeCanvas_LayoutUpdated); } private ItemsControl itemsControl; public ItemsControl ItemsControl { get { return itemsControl; } set { itemsControl = value; if (itemsControl != null) { itemsControl.Measure( new Size(Double.PositiveInfinity, Double.PositiveInfinity)); this.Width = itemsControl.DesiredSize.Width; this.Height = itemsControl.DesiredSize.Height; SetTop(itemsControl, 0); SetLeft(itemsControl, 0); this.Children.Add(itemsControl); } } } void FakeCanvas_LayoutUpdated( object sender, EventArgs e) { if (ItemsControl == null) { return; } if (this.Children.Count == 1) { if (this.Children[0] == ItemsControl) { return; } } ItemsControl.Items.Clear(); List<UIElement> move = new List<UIElement>(); foreach (UIElement child in this.Children) { if (child != ItemsControl) { move.Add(child); } } move.Sort( (ele1, ele2) => Canvas.GetTop(ele1).CompareTo( Canvas.GetTop(ele2))); foreach (UIElement child in move) { this.Children.Remove(child); ItemsControl.Items.Add(child); } ItemsControl.Measure( new Size(Double.PositiveInfinity, Double.PositiveInfinity)); this.Width = itemsControl.DesiredSize.Width; this.Height = itemsControl.DesiredSize.Height; SetTop(itemsControl, 0); SetLeft(itemsControl, 0); if (ItemsControl.Parent == null) { this.Children.Add(ItemsControl); } } }
The changes to the legend style:
<igChart:XamWebChart.Legend> <igChart:Legend Width="100"> <igChart:Legend.Style> <Style TargetType="igChart:Legend"> <Setter Property="Template"> <Setter.Value> <ControlTemplate TargetType="igChart:Legend"> <Border Background="{TemplateBinding Background}" BorderBrush="{TemplateBinding BorderBrush}" BorderThickness="{TemplateBinding BorderThickness}"> <local:FakeCanvas x:Name="RootElement" > <local:FakeCanvas.ItemsControl> <ListBox Height="100" Width="100" /> </local:FakeCanvas.ItemsControl> </local:FakeCanvas> </Border> </ControlTemplate> </Setter.Value> </Setter> </Style> </igChart:Legend.Style> </igChart:Legend> </igChart:XamWebChart.Legend>
I believe the items collection is only being used if you are specifying custom legend items rather than using the autogenerated legend items. The legend for this chart expects its control template to contain a canvas called RootElement into which it absolutely positions the legend items. So if this isnt present, the legend cannot function appropriately. However, it also expects this canvas to be stretched, and then will position the items accordingly. Your best bet is to take the number of legend items you expect and use this to define the height of the canvas you are putting in the scrollviewer. Does that help, or can I explain further?