#region Setup using System; using System.Collections.Generic; using System.Globalization; using System.IO; using System.Linq; using ChartForgeX.Core; using ChartForgeX.Primitives; using ChartForgeX.Rendering; using ChartForgeX.Themes; using ChartForgeX.Topology; using ChartForgeX.Typography; using ChartForgeX.VisualArtifacts; using ChartForgeX.VisualBlocks; var mode = VisualThemeMode.Light; var theme = VisualTheme.Graphite(); var model = AutomaticRadialBandsRecipe.Create("automatic-rings", mode); var context = new VisualRenderContext( new VisualLayoutOptions(new VisualSize(900, 600)), theme, mode, new VisualFrame("Three independent service mixes", "Source order allocates rings; every period keeps its own total", showLegend: null, showSurface: false)); var prepared = model.Prepare(context); File.WriteAllText("visual.svg", prepared.ToSvg()); File.WriteAllBytes("visual.png", prepared.ToPng()); File.WriteAllText("visual.html", prepared.ToArtifact("example", VisualArtifactKind.Chart).ToHtmlPage()); #endregion /// Three independent service mixes use source-ordered automatic Donut bands. public static class AutomaticRadialBandsRecipe { /// Creates immutable allocation without assigning or changing authored RadialBand values. public static Chart Create(string variant = "automatic-rings", VisualThemeMode mode = VisualThemeMode.Light) { if (variant is not ("automatic-rings" or "compact-automatic-rings")) throw new ArgumentOutOfRangeException(nameof(variant)); var chart = Chart.Create().WithXLabels("Subscriptions", "Consulting", "Support") .WithAutomaticRadialBands(new ChartRadialBandAllocation(.2, .04)).WithDonutCenterLabel(false) .WithPieSliceLabelContent(ChartPieSliceLabelContent.LabelAndPercent); var values = new[] { new[] { 50d, 30, 20 }, new[] { 90d, 45, 15 }, new[] { 110d, 66, 44 } }; for (var index = 0; index < values.Length; index++) { var series = new ChartSeries(new ChartSeriesId("period-" + index), "Period " + (index + 1), ChartSeriesKind.Donut, values[index].Select((value, category) => new ChartPoint(category + 1, value))) .WithObservationIds(new[] { new ChartObservationId("subscriptions"), new ChartObservationId("consulting"), new ChartObservationId("support") }) .WithDataLabels(index == values.Length - 1); if (index == values.Length - 1) { series.DataLabelPlacement = ChartDataLabelPlacement.Outside; series.WithPointSliceRadiusRatio(0, .35).WithPointSliceRadiusRatio(1, .7).WithPointSliceRadiusRatio(2, 1); } chart.AddSeries(series); } return chart; } }