Skip to content
This repository was archived by the owner on Jan 9, 2023. It is now read-only.

Commit 76b01cb

Browse files
Googlerstuartmorgan-g
Googler
authored andcommitted
Add functions to draw horizontal or vertical links onto the dart charts web canvas.
PiperOrigin-RevId: 393802496
1 parent 0da1a7e commit 76b01cb

File tree

6 files changed

+247
-1
lines changed

6 files changed

+247
-1
lines changed

charts_common/lib/common.dart

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -198,7 +198,7 @@ export 'src/chart/common/behavior/zoom/panning_tick_provider.dart'
198198
export 'src/chart/common/canvas_shapes.dart'
199199
show CanvasBarStack, CanvasPie, CanvasPieSlice, CanvasRect;
200200
export 'src/chart/common/chart_canvas.dart'
201-
show ChartCanvas, FillPatternType, BlendMode;
201+
show ChartCanvas, FillPatternType, BlendMode, LinkOrientation, Link;
202202
export 'src/chart/common/chart_context.dart' show ChartContext;
203203
export 'src/chart/common/datum_details.dart'
204204
show DatumDetails, DomainFormatter, MeasureFormatter;
@@ -267,6 +267,8 @@ export 'src/chart/treemap/treemap_label_decorator.dart'
267267
export 'src/chart/treemap/treemap_renderer_config.dart'
268268
show TreeMapRendererConfig, TreeMapTileType;
269269
export 'src/common/color.dart' show Color;
270+
export 'src/chart/link/link_chart.dart' show LinkChart;
271+
export 'src/chart/link/link_renderer_config.dart' show LinkRendererConfig;
270272
export 'src/common/date_time_factory.dart'
271273
show DateTimeFactory, LocalDateTimeFactory, UTCDateTimeFactory;
272274
export 'src/common/gesture_listener.dart' show GestureListener;

charts_common/lib/src/chart/common/chart_canvas.dart

Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -45,6 +45,16 @@ abstract class ChartCanvas {
4545
double startAngle, double endAngle,
4646
{Color? fill, Color? stroke, double? strokeWidthPx});
4747

48+
/// Draws a smooth link from source to target.
49+
///
50+
/// [sourceUpper] The location of the upper link at the source node.
51+
/// [sourceLower] The location of the lower link at the source node.
52+
/// [targetUpper] The location of the upper link at the target node.
53+
/// [targetLower] The location of the lower link at the target node.
54+
/// [fill] The fill color for the link.
55+
/// [orientation] Orientation enum of the link, vertical or horizontal.
56+
void drawLink(Link link, LinkOrientation orientation, Color fill);
57+
4858
/// Renders a simple line.
4959
///
5060
/// [dashPattern] controls the pattern of dashes and gaps in a line. It is a
@@ -199,3 +209,25 @@ enum BlendMode {
199209
sourceOver,
200210
xor
201211
}
212+
213+
/// Determines the orientation of a drawn link.
214+
///
215+
/// * [horizontal] Link control points are averaged across the x-axis.
216+
/// * [vertical] Link control points are averaged across the y-axis.
217+
enum LinkOrientation { horizontal, vertical }
218+
219+
/// A link as defined by the two sets of points that determine the bezier
220+
/// curves of the link.
221+
///
222+
/// [sourceUpper] The location of the upper link at the source node.
223+
/// [sourceLower] The location of the lower link at the source node.
224+
/// [targetUpper] The location of the upper link at the target node.
225+
/// [targetLower] The location of the lower link at the target node.
226+
class Link {
227+
final Point sourceUpper;
228+
final Point sourceLower;
229+
final Point targetUpper;
230+
final Point targetLower;
231+
232+
Link(this.sourceUpper, this.sourceLower, this.targetUpper, this.targetLower);
233+
}
Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,39 @@
1+
// Copyright 2021 the Charts project authors. Please see the AUTHORS file
2+
// for details.
3+
//
4+
// Licensed under the Apache License, Version 2.0 (the "License");
5+
// you may not use this file except in compliance with the License.
6+
// You may obtain a copy of the License at
7+
//
8+
// http://www.apache.org/licenses/LICENSE-2.0
9+
//
10+
// Unless required by applicable law or agreed to in writing, software
11+
// distributed under the License is distributed on an "AS IS" BASIS,
12+
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
// See the License for the specific language governing permissions and
14+
// limitations under the License.
15+
16+
import 'package:charts_common/src/chart/common/base_chart.dart';
17+
import 'package:charts_common/src/chart/common/datum_details.dart';
18+
import 'package:charts_common/src/chart/common/selection_model/selection_model.dart';
19+
import 'package:charts_common/src/chart/common/series_renderer.dart';
20+
import 'package:charts_common/src/chart/layout/layout_config.dart';
21+
22+
import 'package:charts_common/src/chart/link/link_renderer.dart';
23+
24+
class LinkChart<D> extends BaseChart<D> {
25+
LinkChart({LayoutConfig? layoutConfig})
26+
: super(layoutConfig: layoutConfig ?? LayoutConfig());
27+
28+
/// Uses LinkRenderer as the default renderer.
29+
@override
30+
SeriesRenderer<D> makeDefaultRenderer() {
31+
return LinkRenderer<D>()..rendererId = SeriesRenderer.defaultRendererId;
32+
}
33+
34+
/// Returns a list of datum details from the selection model of [type].
35+
@override
36+
List<DatumDetails<D>> getDatumDetails(SelectionModelType type) {
37+
return <DatumDetails<D>>[];
38+
}
39+
}
Lines changed: 117 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,117 @@
1+
// Copyright 2021 the Charts project authors. Please see the AUTHORS file
2+
// for details.
3+
//
4+
// Licensed under the Apache License, Version 2.0 (the "License");
5+
// you may not use this file except in compliance with the License.
6+
// You may obtain a copy of the License at
7+
//
8+
// http://www.apache.org/licenses/LICENSE-2.0
9+
//
10+
// Unless required by applicable law or agreed to in writing, software
11+
// distributed under the License is distributed on an "AS IS" BASIS,
12+
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
// See the License for the specific language governing permissions and
14+
// limitations under the License.
15+
16+
import 'dart:collection' show LinkedHashMap;
17+
import 'dart:math' show Point, Rectangle;
18+
19+
import 'package:charts_common/src/chart/common/chart_canvas.dart';
20+
import 'package:charts_common/src/chart/common/datum_details.dart';
21+
import 'package:charts_common/src/chart/common/processed_series.dart';
22+
import 'package:charts_common/src/chart/common/series_datum.dart';
23+
import 'package:charts_common/src/chart/common/series_renderer.dart';
24+
import '../../data/series.dart' show AttributeKey;
25+
import 'package:charts_common/src/common/math.dart' show NullablePoint;
26+
import 'package:charts_common/common.dart' show Color, LinkOrientation, Link;
27+
28+
import 'link_renderer_config.dart';
29+
30+
const linkElementsKey =
31+
AttributeKey<List<LinkRendererElement>>('LinkRenderer.elements');
32+
33+
class LinkRenderer<D> extends BaseSeriesRenderer<D> {
34+
/// Default renderer ID for the Sankey Chart
35+
static const defaultRendererID = 'sankey';
36+
37+
// List of renderer elements to be drawn on the canvas
38+
final _seriesLinkMap = LinkedHashMap<String, List<LinkRendererElement>>();
39+
40+
/// Link Renderer Config
41+
final LinkRendererConfig<D> config;
42+
43+
factory LinkRenderer({String? rendererId, LinkRendererConfig<D>? config}) {
44+
return LinkRenderer._internal(
45+
rendererId: rendererId ?? defaultRendererID,
46+
config: config ?? LinkRendererConfig());
47+
}
48+
49+
LinkRenderer._internal({required String rendererId, required this.config})
50+
: super(
51+
rendererId: rendererId,
52+
layoutPaintOrder: config.layoutPaintOrder,
53+
symbolRenderer: config.symbolRenderer);
54+
55+
@override
56+
void preprocessSeries(List<MutableSeries<D>> seriesList) {
57+
seriesList.forEach((MutableSeries<D> series) {
58+
var elements = <LinkRendererElement>[];
59+
for (var linkIndex = 0; linkIndex < series.data.length; linkIndex++) {
60+
var element = LinkRendererElement(
61+
series.data[linkIndex].link,
62+
series.data[linkIndex].orientation,
63+
series.data[linkIndex].fillColor);
64+
elements.add(element);
65+
}
66+
series.setAttr(linkElementsKey, elements);
67+
});
68+
}
69+
70+
@override
71+
void update(List<ImmutableSeries<D>> seriesList, bool isAnimating) {
72+
seriesList.forEach((ImmutableSeries<D> series) {
73+
var elementsList =
74+
series.getAttr(linkElementsKey) as List<LinkRendererElement>;
75+
_seriesLinkMap.putIfAbsent(series.id, () => elementsList);
76+
});
77+
}
78+
79+
@override
80+
void paint(ChartCanvas canvas, double animationPercent) {
81+
/// Paint the renderer elements on the canvas using drawLink.
82+
_seriesLinkMap.forEach((k, v) => _drawAllLinks(v, canvas));
83+
}
84+
85+
void _drawAllLinks(List<LinkRendererElement> links, ChartCanvas canvas) {
86+
links.forEach((element) =>
87+
canvas.drawLink(element.link, element.orientation, element.fillColor));
88+
}
89+
90+
@override
91+
DatumDetails<D> addPositionToDetailsForSeriesDatum(
92+
DatumDetails<D> details, SeriesDatum<D> seriesDatum) {
93+
final chartPosition = Point<double>(0, 0);
94+
return DatumDetails.from(details,
95+
chartPosition: NullablePoint.from(chartPosition));
96+
}
97+
98+
/// Datum details of nearest link.
99+
@override
100+
List<DatumDetails<D>> getNearestDatumDetailPerSeries(
101+
Point<double> chartPoint,
102+
bool byDomain,
103+
Rectangle<int>? boundsOverride, {
104+
bool selectOverlappingPoints = false,
105+
bool selectExactEventLocation = false,
106+
}) {
107+
return <DatumDetails<D>>[];
108+
}
109+
}
110+
111+
class LinkRendererElement {
112+
final Link link;
113+
final LinkOrientation orientation;
114+
final Color fillColor;
115+
116+
LinkRendererElement(this.link, this.orientation, this.fillColor);
117+
}
Lines changed: 47 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,47 @@
1+
// Copyright 2021 the Charts project authors. Please see the AUTHORS file
2+
// for details.
3+
//
4+
// Licensed under the Apache License, Version 2.0 (the "License");
5+
// you may not use this file except in compliance with the License.
6+
// You may obtain a copy of the License at
7+
//
8+
// http://www.apache.org/licenses/LICENSE-2.0
9+
//
10+
// Unless required by applicable law or agreed to in writing, software
11+
// distributed under the License is distributed on an "AS IS" BASIS,
12+
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
// See the License for the specific language governing permissions and
14+
// limitations under the License.
15+
16+
import 'package:charts_common/src/chart/common/series_renderer_config.dart';
17+
import 'package:charts_common/src/chart/layout/layout_view.dart';
18+
import 'package:charts_common/src/common/symbol_renderer.dart';
19+
20+
import 'link_renderer.dart';
21+
22+
/// Configuration for a [SankeyRenderer].
23+
class LinkRendererConfig<D> extends LayoutViewConfig
24+
implements SeriesRendererConfig<D> {
25+
@override
26+
final String? customRendererId;
27+
28+
@override
29+
final SymbolRenderer symbolRenderer;
30+
31+
@override
32+
final rendererAttributes = RendererAttributes();
33+
34+
/// The order to paint this renderer on the canvas.
35+
final int layoutPaintOrder;
36+
37+
LinkRendererConfig(
38+
{this.customRendererId,
39+
this.layoutPaintOrder = LayoutViewPaintOrder.bar,
40+
SymbolRenderer? symbolRenderer})
41+
: symbolRenderer = symbolRenderer ?? RectSymbolRenderer();
42+
43+
@override
44+
LinkRenderer<D> build() {
45+
return LinkRenderer<D>(config: this, rendererId: customRendererId);
46+
}
47+
}

charts_flutter/lib/src/chart_canvas.dart

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,8 @@ import 'package:charts_common/common.dart' as common
2424
Color,
2525
FillPatternType,
2626
GraphicsFactory,
27+
Link,
28+
LinkOrientation,
2729
StyleFactory,
2830
TextElement,
2931
TextDirection;
@@ -61,6 +63,13 @@ class ChartCanvas implements common.ChartCanvas {
6163
);
6264
}
6365

66+
@override
67+
void drawLink(
68+
common.Link link, common.LinkOrientation orientation, common.Color fill) {
69+
// TODO: Implement drawLink for flutter.
70+
throw ("Flutter drawLink() has not been implemented.");
71+
}
72+
6473
@override
6574
void drawLine(
6675
{required List<Point> points,

0 commit comments

Comments
 (0)