From a831f2a88012c0e9e6dacced7631419107dbfbc8 Mon Sep 17 00:00:00 2001 From: Jani Koponen Date: Wed, 22 Nov 2023 16:58:35 +0200 Subject: [PATCH 01/27] Add padding and margin for tooltips --- lib/src/chart/bar_chart/bar_chart_data.dart | 19 ++++++--- .../chart/bar_chart/bar_chart_painter.dart | 31 ++++++++++---- .../base/axis_chart/axis_chart_painter.dart | 9 ++++- lib/src/chart/line_chart/line_chart_data.dart | 16 +++++--- .../chart/line_chart/line_chart_painter.dart | 39 +++++++++++++----- .../scatter_chart/scatter_chart_data.dart | 9 ++++- .../scatter_chart/scatter_chart_painter.dart | 24 ++++++++++- test/chart/data_pool.dart | 40 +++++++++---------- 8 files changed, 135 insertions(+), 52 deletions(-) diff --git a/lib/src/chart/bar_chart/bar_chart_data.dart b/lib/src/chart/bar_chart/bar_chart_data.dart index 7597e5714..dceeb8dd8 100644 --- a/lib/src/chart/bar_chart/bar_chart_data.dart +++ b/lib/src/chart/bar_chart/bar_chart_data.dart @@ -689,8 +689,9 @@ class BarTouchTooltipData with EquatableMixin { /// otherwise you can show it manually using [BarChartGroupData.showingTooltipIndicators]. /// Tooltip shows on top of rods, with [tooltipBgColor] as a background color, /// and you can set corner radius using [tooltipRoundedRadius]. - /// If you want to have a padding inside the tooltip, fill [tooltipPadding], - /// or If you want to have a bottom margin, set [tooltipMargin]. + /// If you want to have tooltip padding, fill [tooltipPadding], + /// If you want to have tooltip margin, fill [tooltipMargin]. + /// If you want to adjust tooltip vertical position, set [tooltipVerticalOffset] /// Content of the tooltip will provide using [getTooltipItem] callback, you can override it /// and pass your custom data to show in the tooltip. /// You can restrict the tooltip's width using [maxContentWidth]. @@ -701,7 +702,8 @@ class BarTouchTooltipData with EquatableMixin { Color? tooltipBgColor, double? tooltipRoundedRadius, EdgeInsets? tooltipPadding, - double? tooltipMargin, + EdgeInsets? tooltipMargin, + double? tooltipVerticalOffset, FLHorizontalAlignment? tooltipHorizontalAlignment, double? tooltipHorizontalOffset, double? maxContentWidth, @@ -715,7 +717,8 @@ class BarTouchTooltipData with EquatableMixin { tooltipRoundedRadius = tooltipRoundedRadius ?? 4, tooltipPadding = tooltipPadding ?? const EdgeInsets.symmetric(horizontal: 16, vertical: 8), - tooltipMargin = tooltipMargin ?? 16, + tooltipMargin = tooltipMargin ?? const EdgeInsets.only(bottom: 8), + tooltipVerticalOffset = tooltipVerticalOffset ?? 16, tooltipHorizontalAlignment = tooltipHorizontalAlignment ?? FLHorizontalAlignment.center, tooltipHorizontalOffset = tooltipHorizontalOffset ?? 0, @@ -737,8 +740,11 @@ class BarTouchTooltipData with EquatableMixin { /// Applies a padding for showing contents inside the tooltip. final EdgeInsets tooltipPadding; - /// Applies a bottom margin for showing tooltip on top of rods. - final double tooltipMargin; + /// Applies a margin for content + final EdgeInsets tooltipMargin; + + /// Adds a offset for tooltip vertical position (offset is applied to bottom of the tooltip) for showing tooltip on top of rods. + final double tooltipVerticalOffset; /// Controls showing tooltip on left side, right side or center aligned with rod, default is center final FLHorizontalAlignment tooltipHorizontalAlignment; @@ -774,6 +780,7 @@ class BarTouchTooltipData with EquatableMixin { tooltipRoundedRadius, tooltipPadding, tooltipMargin, + tooltipVerticalOffset, tooltipHorizontalAlignment, tooltipHorizontalOffset, maxContentWidth, diff --git a/lib/src/chart/bar_chart/bar_chart_painter.dart b/lib/src/chart/bar_chart/bar_chart_painter.dart index ff7a41347..1d1337bc5 100644 --- a/lib/src/chart/bar_chart/bar_chart_painter.dart +++ b/lib/src/chart/bar_chart/bar_chart_painter.dart @@ -344,8 +344,6 @@ class BarChartPainter extends AxisChartPainter { ) { final viewSize = canvasWrapper.size; - const textsBelowMargin = 4; - final tooltipItem = tooltipData.getTooltipItem( showOnBarGroup, barGroupIndex, @@ -381,7 +379,7 @@ class BarChartPainter extends AxisChartPainter { /// sum up all Texts height, then we should /// draw the tooltip's height as tall as sumTextsHeight final textWidth = drawingTextPainter.width; - final textHeight = drawingTextPainter.height + textsBelowMargin; + final textHeight = drawingTextPainter.height; /// if we have multiple bar lines, /// there are more than one FlCandidate on touch area, @@ -405,25 +403,44 @@ class BarChartPainter extends AxisChartPainter { (tooltipData.direction == TooltipDirection.auto && showOnRodData.isUpward()); final tooltipTop = drawTooltipOnTop - ? barTopY - tooltipHeight - tooltipData.tooltipMargin - : barBottomY + tooltipData.tooltipMargin; - + ? barTopY - tooltipHeight - tooltipData.tooltipVerticalOffset + : barBottomY + tooltipData.tooltipVerticalOffset; final tooltipLeft = getTooltipLeft( barToYPixel.dx, tooltipWidth, tooltipData.tooltipHorizontalAlignment, tooltipData.tooltipHorizontalOffset, + tooltipData.tooltipPadding, ); /// draw the background rect with rounded radius // ignore: omit_local_variable_types - Rect rect = Rect.fromLTWH( + final backgroundRect = Rect.fromLTWH( tooltipLeft, tooltipTop, tooltipWidth, tooltipHeight, ); + /// Apply padding to background rect + var rect = Rect.fromLTRB( + backgroundRect.left - tooltipData.tooltipPadding.left, + backgroundRect.top - tooltipData.tooltipPadding.top, + backgroundRect.right + tooltipData.tooltipPadding.right, + backgroundRect.bottom + tooltipData.tooltipPadding.bottom, + ); + + /// Apply margin to background rect + /// Since margin is meant for outside the object, we can mimic it by shifting the object center + rect = Rect.fromCenter( + center: Offset( + rect.center.dx + tooltipData.tooltipMargin.horizontal, + rect.center.dy - tooltipData.tooltipMargin.vertical, + ), + width: rect.width, + height: rect.height, + ); + if (tooltipData.fitInsideHorizontally) { if (rect.left < 0) { final shiftAmount = 0 - rect.left; diff --git a/lib/src/chart/base/axis_chart/axis_chart_painter.dart b/lib/src/chart/base/axis_chart/axis_chart_painter.dart index 833b7ee91..4a2dc92c2 100644 --- a/lib/src/chart/base/axis_chart/axis_chart_painter.dart +++ b/lib/src/chart/base/axis_chart/axis_chart_painter.dart @@ -439,19 +439,24 @@ abstract class AxisChartPainter /// With this function we can get horizontal /// position for the tooltip. + /// double getTooltipLeft( double dx, double tooltipWidth, FLHorizontalAlignment tooltipHorizontalAlignment, double tooltipHorizontalOffset, + EdgeInsets tooltipPadding, ) { switch (tooltipHorizontalAlignment) { case FLHorizontalAlignment.center: return dx - (tooltipWidth / 2) + tooltipHorizontalOffset; case FLHorizontalAlignment.right: - return dx + tooltipHorizontalOffset; + return dx + tooltipHorizontalOffset + (tooltipPadding.horizontal / 2); case FLHorizontalAlignment.left: - return dx - tooltipWidth + tooltipHorizontalOffset; + return dx - + tooltipWidth + + tooltipHorizontalOffset - + (tooltipPadding.horizontal / 2); } } } diff --git a/lib/src/chart/line_chart/line_chart_data.dart b/lib/src/chart/line_chart/line_chart_data.dart index b09a1b029..604295dff 100644 --- a/lib/src/chart/line_chart/line_chart_data.dart +++ b/lib/src/chart/line_chart/line_chart_data.dart @@ -1024,8 +1024,9 @@ class LineTouchTooltipData with EquatableMixin { /// otherwise you can show it manually using [LineChartData.showingTooltipIndicators]. /// Tooltip shows on top of spots, with [tooltipBgColor] as a background color, /// and you can set corner radius using [tooltipRoundedRadius]. - /// If you want to have a padding inside the tooltip, fill [tooltipPadding], - /// or If you want to have a bottom margin, set [tooltipMargin]. + /// If you want to have tooltip padding, fill [tooltipPadding], + /// If you want to have tooltip margin, fill [tooltipMargin]. + /// If you want to adjust tooltip vertical position, set [tooltipVerticalOffset] /// Content of the tooltip will provide using [getTooltipItems] callback, you can override it /// and pass your custom data to show in the tooltip. /// You can restrict the tooltip's width using [maxContentWidth]. @@ -1037,7 +1038,8 @@ class LineTouchTooltipData with EquatableMixin { this.tooltipRoundedRadius = 4, this.tooltipPadding = const EdgeInsets.symmetric(horizontal: 16, vertical: 8), - this.tooltipMargin = 16, + this.tooltipMargin = const EdgeInsets.only(bottom: 8), + this.tooltipVerticalOffset = 16, this.tooltipHorizontalAlignment = FLHorizontalAlignment.center, this.tooltipHorizontalOffset = 0, this.maxContentWidth = 120, @@ -1058,8 +1060,11 @@ class LineTouchTooltipData with EquatableMixin { /// Applies a padding for showing contents inside the tooltip. final EdgeInsets tooltipPadding; - /// Applies a bottom margin for showing tooltip on top of rods. - final double tooltipMargin; + /// Applies a margin for content + final EdgeInsets tooltipMargin; + + /// Adds a offset for tooltip vertical position (offset is applied to bottom of the tooltip) for showing tooltip on top of rods. + final double tooltipVerticalOffset; /// Controls showing tooltip on left side, right side or center aligned with spot, default is center final FLHorizontalAlignment tooltipHorizontalAlignment; @@ -1095,6 +1100,7 @@ class LineTouchTooltipData with EquatableMixin { tooltipRoundedRadius, tooltipPadding, tooltipMargin, + tooltipVerticalOffset, tooltipHorizontalAlignment, tooltipHorizontalOffset, maxContentWidth, diff --git a/lib/src/chart/line_chart/line_chart_painter.dart b/lib/src/chart/line_chart/line_chart_painter.dart index 75b4a60ec..cf2818348 100644 --- a/lib/src/chart/line_chart/line_chart_painter.dart +++ b/lib/src/chart/line_chart/line_chart_painter.dart @@ -988,7 +988,7 @@ class LineChartPainter extends AxisChartPainter { ) { final viewSize = canvasWrapper.size; - const textsBelowMargin = 4; + const textsBelowPadding = 4; /// creating TextPainters to calculate the width and height of the tooltip final drawingTextPainters = []; @@ -1038,7 +1038,7 @@ class LineChartPainter extends AxisChartPainter { } sumTextsHeight += tp.height; } - sumTextsHeight += (drawingTextPainters.length - 1) * textsBelowMargin; + sumTextsHeight += (drawingTextPainters.length - 1) * textsBelowPadding; /// if we have multiple bar lines, /// there are more than one FlCandidate on touch area, @@ -1048,15 +1048,16 @@ class LineChartPainter extends AxisChartPainter { getPixelY(showOnSpot.y, viewSize, holder), ); - final tooltipWidth = biggerWidth + tooltipData.tooltipPadding.horizontal; - final tooltipHeight = sumTextsHeight + tooltipData.tooltipPadding.vertical; + final tooltipWidth = biggerWidth; + final tooltipHeight = sumTextsHeight; double tooltipTopPosition; if (tooltipData.showOnTopOfTheChartBoxArea) { - tooltipTopPosition = 0 - tooltipHeight - tooltipData.tooltipMargin; + tooltipTopPosition = + 0 - tooltipHeight - tooltipData.tooltipVerticalOffset; } else { tooltipTopPosition = - mostTopOffset.dy - tooltipHeight - tooltipData.tooltipMargin; + mostTopOffset.dy - tooltipHeight - tooltipData.tooltipVerticalOffset; } final tooltipLeftPosition = getTooltipLeft( @@ -1064,16 +1065,36 @@ class LineChartPainter extends AxisChartPainter { tooltipWidth, tooltipData.tooltipHorizontalAlignment, tooltipData.tooltipHorizontalOffset, + tooltipData.tooltipPadding, ); /// draw the background rect with rounded radius - var rect = Rect.fromLTWH( + final backgroundRect = Rect.fromLTWH( tooltipLeftPosition, tooltipTopPosition, tooltipWidth, tooltipHeight, ); + /// Apply padding to background rect + var rect = Rect.fromLTRB( + backgroundRect.left - tooltipData.tooltipPadding.left, + backgroundRect.top - tooltipData.tooltipPadding.top, + backgroundRect.right + tooltipData.tooltipPadding.right, + backgroundRect.bottom + tooltipData.tooltipPadding.bottom, + ); + + /// Apply margin to background rect + /// Since margin affects outside area of the object, we can mimic it by shifting the object center + rect = Rect.fromCenter( + center: Offset( + rect.center.dx + tooltipData.tooltipMargin.horizontal, + rect.center.dy - tooltipData.tooltipMargin.vertical, + ), + width: rect.width, + height: rect.height, + ); + if (tooltipData.fitInsideHorizontally) { if (rect.left < 0) { final shiftAmount = 0 - rect.left; @@ -1166,7 +1187,7 @@ class LineChartPainter extends AxisChartPainter { final xOffset = switch (align) { HorizontalAlignment.left => rect.left + tooltipData.tooltipPadding.left, HorizontalAlignment.right => - rect.right - tooltipData.tooltipPadding.right - tp.width, + rect.right - tooltipData.tooltipMargin.right - tp.width, _ => rect.center.dx - (tp.width / 2), }; @@ -1185,7 +1206,7 @@ class LineChartPainter extends AxisChartPainter { }, ); topPosSeek += tp.height; - topPosSeek += textsBelowMargin; + topPosSeek += textsBelowPadding; } } diff --git a/lib/src/chart/scatter_chart/scatter_chart_data.dart b/lib/src/chart/scatter_chart/scatter_chart_data.dart index 5bb9c9d81..14966cea1 100644 --- a/lib/src/chart/scatter_chart/scatter_chart_data.dart +++ b/lib/src/chart/scatter_chart/scatter_chart_data.dart @@ -403,6 +403,7 @@ class ScatterTouchTooltipData with EquatableMixin { Color? tooltipBgColor, double? tooltipRoundedRadius, EdgeInsets? tooltipPadding, + EdgeInsets? tooltipMargin, FLHorizontalAlignment? tooltipHorizontalAlignment, double? tooltipHorizontalOffset, double? maxContentWidth, @@ -413,8 +414,8 @@ class ScatterTouchTooltipData with EquatableMixin { BorderSide? tooltipBorder, }) : tooltipBgColor = tooltipBgColor ?? Colors.blueGrey.darken(15), tooltipRoundedRadius = tooltipRoundedRadius ?? 4, - tooltipPadding = tooltipPadding ?? - const EdgeInsets.symmetric(horizontal: 16, vertical: 8), + tooltipPadding = tooltipPadding ?? const EdgeInsets.all(6), + tooltipMargin = tooltipMargin ?? EdgeInsets.zero, tooltipHorizontalAlignment = tooltipHorizontalAlignment ?? FLHorizontalAlignment.center, tooltipHorizontalOffset = tooltipHorizontalOffset ?? 0, @@ -435,6 +436,9 @@ class ScatterTouchTooltipData with EquatableMixin { /// Applies a padding for showing contents inside the tooltip. final EdgeInsets tooltipPadding; + /// Applies a margin for content + final EdgeInsets tooltipMargin; + /// Controls showing tooltip on left side, right side or center aligned with spot, default is center final FLHorizontalAlignment tooltipHorizontalAlignment; @@ -464,6 +468,7 @@ class ScatterTouchTooltipData with EquatableMixin { List get props => [ tooltipBgColor, tooltipRoundedRadius, + tooltipMargin, tooltipPadding, tooltipHorizontalAlignment, tooltipHorizontalOffset, diff --git a/lib/src/chart/scatter_chart/scatter_chart_painter.dart b/lib/src/chart/scatter_chart/scatter_chart_painter.dart index 386079d76..27b05eeee 100644 --- a/lib/src/chart/scatter_chart/scatter_chart_painter.dart +++ b/lib/src/chart/scatter_chart/scatter_chart_painter.dart @@ -246,10 +246,11 @@ class ScatterChartPainter extends AxisChartPainter { tooltipWidth, tooltipData.tooltipHorizontalAlignment, tooltipData.tooltipHorizontalOffset, + tooltipData.tooltipPadding, ); /// draw the background rect with rounded radius - var rect = Rect.fromLTWH( + final backgroundRect = Rect.fromLTWH( tooltipLeftPosition, mostTopOffset.dy - tooltipHeight - @@ -259,6 +260,27 @@ class ScatterChartPainter extends AxisChartPainter { tooltipHeight, ); + /// Apply padding to background rect + var rect = Rect.fromLTRB( + backgroundRect.left - tooltipData.tooltipPadding.left, + backgroundRect.top - tooltipData.tooltipPadding.top, + backgroundRect.right + tooltipData.tooltipPadding.right, + backgroundRect.bottom + + tooltipData.tooltipPadding.bottom - + tooltipItem.bottomMargin, + ); + + /// Apply margin to background rect + /// Since margin affects outside area of the object, we can mimic it by shifting the object center + rect = Rect.fromCenter( + center: Offset( + rect.center.dx + tooltipData.tooltipMargin.horizontal, + rect.center.dy - tooltipData.tooltipMargin.vertical, + ), + width: rect.width, + height: rect.height, + ); + if (tooltipData.fitInsideHorizontally) { if (rect.left < 0) { final shiftAmount = 0 - rect.left; diff --git a/test/chart/data_pool.dart b/test/chart/data_pool.dart index d60bef0fa..15878f51e 100644 --- a/test/chart/data_pool.dart +++ b/test/chart/data_pool.dart @@ -1189,7 +1189,7 @@ const LineTouchTooltipData lineTouchTooltipData1 = LineTouchTooltipData( getTooltipItems: lineChartGetTooltipItems, fitInsideHorizontally: true, tooltipRoundedRadius: 12, - tooltipMargin: 33, + tooltipVerticalOffset: 33, tooltipBorder: BorderSide(color: Colors.red), ); const LineTouchTooltipData lineTouchTooltipData1Clone = LineTouchTooltipData( @@ -1199,7 +1199,7 @@ const LineTouchTooltipData lineTouchTooltipData1Clone = LineTouchTooltipData( getTooltipItems: lineChartGetTooltipItems, fitInsideHorizontally: true, tooltipRoundedRadius: 12, - tooltipMargin: 33, + tooltipVerticalOffset: 33, tooltipBorder: BorderSide(color: Colors.red), ); @@ -1210,7 +1210,7 @@ const LineTouchTooltipData lineTouchTooltipData2 = LineTouchTooltipData( getTooltipItems: lineChartGetTooltipItems, fitInsideHorizontally: true, tooltipRoundedRadius: 12, - tooltipMargin: 33, + tooltipVerticalOffset: 33, tooltipBorder: BorderSide(color: Colors.red), ); const LineTouchTooltipData lineTouchTooltipData3 = LineTouchTooltipData( @@ -1220,7 +1220,7 @@ const LineTouchTooltipData lineTouchTooltipData3 = LineTouchTooltipData( getTooltipItems: lineChartGetTooltipItems, fitInsideHorizontally: true, tooltipRoundedRadius: 12, - tooltipMargin: 33, + tooltipVerticalOffset: 33, tooltipBorder: BorderSide(color: Colors.red), tooltipHorizontalAlignment: FLHorizontalAlignment.left, ); @@ -1231,7 +1231,7 @@ const LineTouchTooltipData lineTouchTooltipData4 = LineTouchTooltipData( getTooltipItems: lineChartGetTooltipItems, fitInsideHorizontally: true, tooltipRoundedRadius: 12, - tooltipMargin: 33, + tooltipVerticalOffset: 33, tooltipBorder: BorderSide(color: Colors.red), tooltipHorizontalAlignment: FLHorizontalAlignment.right, ); @@ -1242,7 +1242,7 @@ const LineTouchTooltipData lineTouchTooltipData5 = LineTouchTooltipData( getTooltipItems: lineChartGetTooltipItems, fitInsideHorizontally: true, tooltipRoundedRadius: 12, - tooltipMargin: 34, + tooltipVerticalOffset: 34, tooltipBorder: BorderSide(color: Colors.red), tooltipHorizontalOffset: 10, ); @@ -1253,7 +1253,7 @@ const LineTouchTooltipData lineTouchTooltipData6 = LineTouchTooltipData( getTooltipItems: lineChartGetTooltipItems, fitInsideHorizontally: true, tooltipRoundedRadius: 12, - tooltipMargin: 33, + tooltipVerticalOffset: 33, tooltipBorder: BorderSide(color: Colors.pink), tooltipHorizontalAlignment: FLHorizontalAlignment.left, tooltipHorizontalOffset: -10, @@ -1265,7 +1265,7 @@ const LineTouchTooltipData lineTouchTooltipData7 = LineTouchTooltipData( getTooltipItems: lineChartGetTooltipItems, fitInsideHorizontally: true, tooltipRoundedRadius: 12, - tooltipMargin: 33, + tooltipVerticalOffset: 33, tooltipBorder: BorderSide(color: Colors.red, width: 2), tooltipHorizontalAlignment: FLHorizontalAlignment.right, tooltipHorizontalOffset: 10, @@ -2752,7 +2752,7 @@ final BarTouchTooltipData barTouchTooltipData1 = BarTouchTooltipData( tooltipBgColor: Colors.green, tooltipPadding: const EdgeInsets.all(23), getTooltipItem: getTooltipItem, - tooltipMargin: 12, + tooltipVerticalOffset: 12, tooltipBorder: const BorderSide(color: Colors.red), ); final BarTouchTooltipData barTouchTooltipData1Clone = BarTouchTooltipData( @@ -2763,7 +2763,7 @@ final BarTouchTooltipData barTouchTooltipData1Clone = BarTouchTooltipData( tooltipBgColor: Colors.green, tooltipPadding: const EdgeInsets.all(23), getTooltipItem: getTooltipItem, - tooltipMargin: 12, + tooltipVerticalOffset: 12, tooltipBorder: const BorderSide(color: Colors.red), ); final BarTouchTooltipData barTouchTooltipData2 = BarTouchTooltipData( @@ -2774,7 +2774,7 @@ final BarTouchTooltipData barTouchTooltipData2 = BarTouchTooltipData( tooltipBgColor: Colors.green, tooltipPadding: const EdgeInsets.all(23), getTooltipItem: getTooltipItem, - tooltipMargin: 12, + tooltipVerticalOffset: 12, tooltipBorder: const BorderSide(color: Colors.red), tooltipHorizontalAlignment: FLHorizontalAlignment.center, ); @@ -2786,7 +2786,7 @@ final BarTouchTooltipData barTouchTooltipData3 = BarTouchTooltipData( tooltipBgColor: Colors.green, tooltipPadding: const EdgeInsets.all(23), getTooltipItem: getTooltipItem, - tooltipMargin: 12, + tooltipVerticalOffset: 12, tooltipBorder: const BorderSide(color: Colors.red), tooltipHorizontalAlignment: FLHorizontalAlignment.left, ); @@ -2798,7 +2798,7 @@ final BarTouchTooltipData barTouchTooltipData4 = BarTouchTooltipData( tooltipBgColor: Colors.green, tooltipPadding: const EdgeInsets.all(23), getTooltipItem: getTooltipItem, - tooltipMargin: 12, + tooltipVerticalOffset: 12, tooltipBorder: const BorderSide(color: Colors.red), tooltipHorizontalAlignment: FLHorizontalAlignment.right, ); @@ -2810,7 +2810,7 @@ final BarTouchTooltipData barTouchTooltipData5 = BarTouchTooltipData( tooltipBgColor: Colors.green, tooltipPadding: const EdgeInsets.all(23), getTooltipItem: getTooltipItem, - tooltipMargin: 12, + tooltipVerticalOffset: 12, tooltipBorder: const BorderSide(color: Colors.red), tooltipHorizontalAlignment: FLHorizontalAlignment.center, tooltipHorizontalOffset: 10, @@ -2823,7 +2823,7 @@ final BarTouchTooltipData barTouchTooltipData6 = BarTouchTooltipData( tooltipBgColor: Colors.blue, tooltipPadding: const EdgeInsets.all(23), getTooltipItem: getTooltipItem, - tooltipMargin: 12, + tooltipVerticalOffset: 12, tooltipBorder: const BorderSide(color: Colors.red), tooltipHorizontalAlignment: FLHorizontalAlignment.left, tooltipHorizontalOffset: -10, @@ -2835,7 +2835,7 @@ final BarTouchTooltipData barTouchTooltipData7 = BarTouchTooltipData( maxContentWidth: 23, tooltipBgColor: Colors.green, getTooltipItem: getTooltipItem, - tooltipMargin: 12, + tooltipVerticalOffset: 12, tooltipBorder: const BorderSide(color: Colors.red), tooltipHorizontalAlignment: FLHorizontalAlignment.right, tooltipHorizontalOffset: 10, @@ -2847,7 +2847,7 @@ final BarTouchTooltipData barTouchTooltipData8 = BarTouchTooltipData( maxContentWidth: 23, tooltipBgColor: Colors.green, tooltipPadding: const EdgeInsets.all(23), - tooltipMargin: 12, + tooltipVerticalOffset: 12, tooltipBorder: const BorderSide(color: Colors.red), ); final BarTouchTooltipData barTouchTooltipData9 = BarTouchTooltipData( @@ -2858,7 +2858,7 @@ final BarTouchTooltipData barTouchTooltipData9 = BarTouchTooltipData( tooltipBgColor: Colors.green, tooltipPadding: const EdgeInsets.all(23), getTooltipItem: getTooltipItem, - tooltipMargin: 333, + tooltipVerticalOffset: 333, tooltipBorder: const BorderSide(color: Colors.red), ); final BarTouchTooltipData barTouchTooltipData10 = BarTouchTooltipData( @@ -2869,7 +2869,7 @@ final BarTouchTooltipData barTouchTooltipData10 = BarTouchTooltipData( tooltipBgColor: Colors.green, tooltipPadding: const EdgeInsets.all(23), getTooltipItem: getTooltipItem, - tooltipMargin: 12, + tooltipVerticalOffset: 12, tooltipBorder: const BorderSide(color: Colors.blue), ); final BarTouchTooltipData barTouchTooltipData11 = BarTouchTooltipData( @@ -2880,7 +2880,7 @@ final BarTouchTooltipData barTouchTooltipData11 = BarTouchTooltipData( tooltipBgColor: Colors.green, tooltipPadding: const EdgeInsets.all(23), getTooltipItem: getTooltipItem, - tooltipMargin: 12, + tooltipVerticalOffset: 12, tooltipBorder: const BorderSide(color: Colors.red, width: 2), ); From 13c832f34356d975fab3c07041bf0e67854aa4ec Mon Sep 17 00:00:00 2001 From: Jani Koponen Date: Wed, 22 Nov 2023 16:58:43 +0200 Subject: [PATCH 02/27] Fix test mocks --- test/chart/bar_chart/bar_chart_renderer_test.mocks.dart | 2 ++ test/chart/line_chart/line_chart_painter_test.dart | 6 +++--- test/chart/line_chart/line_chart_painter_test.mocks.dart | 3 +++ test/chart/line_chart/line_chart_renderer_test.mocks.dart | 2 ++ .../scatter_chart/scatter_chart_renderer_test.mocks.dart | 2 ++ 5 files changed, 12 insertions(+), 3 deletions(-) diff --git a/test/chart/bar_chart/bar_chart_renderer_test.mocks.dart b/test/chart/bar_chart/bar_chart_renderer_test.mocks.dart index 363495b21..432eda667 100644 --- a/test/chart/bar_chart/bar_chart_renderer_test.mocks.dart +++ b/test/chart/bar_chart/bar_chart_renderer_test.mocks.dart @@ -1515,6 +1515,7 @@ class MockBarChartPainter extends _i1.Mock implements _i10.BarChartPainter { double? tooltipWidth, _i13.FLHorizontalAlignment? tooltipHorizontalAlignment, double? tooltipHorizontalOffset, + _i6.EdgeInsets? tooltipPadding, ) => (super.noSuchMethod( Invocation.method( @@ -1524,6 +1525,7 @@ class MockBarChartPainter extends _i1.Mock implements _i10.BarChartPainter { tooltipWidth, tooltipHorizontalAlignment, tooltipHorizontalOffset, + tooltipPadding, ], ), returnValue: 0.0, diff --git a/test/chart/line_chart/line_chart_painter_test.dart b/test/chart/line_chart/line_chart_painter_test.dart index 8f3b4f759..2180bbaf3 100644 --- a/test/chart/line_chart/line_chart_painter_test.dart +++ b/test/chart/line_chart/line_chart_painter_test.dart @@ -2313,7 +2313,7 @@ void main() { tooltipRoundedRadius: 12, rotateAngle: 43, maxContentWidth: 100, - tooltipMargin: 12, + tooltipVerticalOffset: 12, tooltipPadding: const EdgeInsets.all(12), fitInsideHorizontally: true, fitInsideVertically: true, @@ -2424,7 +2424,7 @@ void main() { tooltipRoundedRadius: 12, rotateAngle: 43, maxContentWidth: 100, - tooltipMargin: 12, + tooltipVerticalOffset: 12, tooltipHorizontalAlignment: FLHorizontalAlignment.left, tooltipPadding: const EdgeInsets.all(12), fitInsideVertically: true, @@ -2535,7 +2535,7 @@ void main() { tooltipRoundedRadius: 12, rotateAngle: 43, maxContentWidth: 100, - tooltipMargin: 12, + tooltipVerticalOffset: 12, tooltipHorizontalAlignment: FLHorizontalAlignment.right, tooltipPadding: const EdgeInsets.all(12), fitInsideVertically: true, diff --git a/test/chart/line_chart/line_chart_painter_test.mocks.dart b/test/chart/line_chart/line_chart_painter_test.mocks.dart index b30a9a838..9526532b4 100644 --- a/test/chart/line_chart/line_chart_painter_test.mocks.dart +++ b/test/chart/line_chart/line_chart_painter_test.mocks.dart @@ -14,6 +14,7 @@ import 'package:fl_chart/src/utils/canvas_wrapper.dart' as _i6; import 'package:fl_chart/src/utils/utils.dart' as _i8; import 'package:flutter/cupertino.dart' as _i3; import 'package:flutter/foundation.dart' as _i4; +import 'package:flutter/material.dart' as _i11; import 'package:mockito/mockito.dart' as _i1; import 'package:mockito/src/dummies.dart' as _i9; @@ -2080,6 +2081,7 @@ class MockLineChartPainter extends _i1.Mock implements _i10.LineChartPainter { double? tooltipWidth, _i7.FLHorizontalAlignment? tooltipHorizontalAlignment, double? tooltipHorizontalOffset, + _i11.EdgeInsets? tooltipPadding, ) => (super.noSuchMethod( Invocation.method( @@ -2089,6 +2091,7 @@ class MockLineChartPainter extends _i1.Mock implements _i10.LineChartPainter { tooltipWidth, tooltipHorizontalAlignment, tooltipHorizontalOffset, + tooltipPadding, ], ), returnValue: 0.0, diff --git a/test/chart/line_chart/line_chart_renderer_test.mocks.dart b/test/chart/line_chart/line_chart_renderer_test.mocks.dart index 8996944ba..7db351bef 100644 --- a/test/chart/line_chart/line_chart_renderer_test.mocks.dart +++ b/test/chart/line_chart/line_chart_renderer_test.mocks.dart @@ -1862,6 +1862,7 @@ class MockLineChartPainter extends _i1.Mock implements _i10.LineChartPainter { double? tooltipWidth, _i13.FLHorizontalAlignment? tooltipHorizontalAlignment, double? tooltipHorizontalOffset, + _i6.EdgeInsets? tooltipPadding, ) => (super.noSuchMethod( Invocation.method( @@ -1871,6 +1872,7 @@ class MockLineChartPainter extends _i1.Mock implements _i10.LineChartPainter { tooltipWidth, tooltipHorizontalAlignment, tooltipHorizontalOffset, + tooltipPadding, ], ), returnValue: 0.0, diff --git a/test/chart/scatter_chart/scatter_chart_renderer_test.mocks.dart b/test/chart/scatter_chart/scatter_chart_renderer_test.mocks.dart index 79cd9ed5b..708dbf51f 100644 --- a/test/chart/scatter_chart/scatter_chart_renderer_test.mocks.dart +++ b/test/chart/scatter_chart/scatter_chart_renderer_test.mocks.dart @@ -1481,6 +1481,7 @@ class MockScatterChartPainter extends _i1.Mock double? tooltipWidth, _i13.FLHorizontalAlignment? tooltipHorizontalAlignment, double? tooltipHorizontalOffset, + _i6.EdgeInsets? tooltipPadding, ) => (super.noSuchMethod( Invocation.method( @@ -1490,6 +1491,7 @@ class MockScatterChartPainter extends _i1.Mock tooltipWidth, tooltipHorizontalAlignment, tooltipHorizontalOffset, + tooltipPadding, ], ), returnValue: 0.0, From 2dd42973d4ce5e3c0a4342aa295da32c0a80184a Mon Sep 17 00:00:00 2001 From: Jani Koponen Date: Thu, 23 Nov 2023 09:39:09 +0200 Subject: [PATCH 03/27] Change margin to zero by default --- lib/src/chart/bar_chart/bar_chart_data.dart | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/src/chart/bar_chart/bar_chart_data.dart b/lib/src/chart/bar_chart/bar_chart_data.dart index dceeb8dd8..987149a5e 100644 --- a/lib/src/chart/bar_chart/bar_chart_data.dart +++ b/lib/src/chart/bar_chart/bar_chart_data.dart @@ -717,7 +717,7 @@ class BarTouchTooltipData with EquatableMixin { tooltipRoundedRadius = tooltipRoundedRadius ?? 4, tooltipPadding = tooltipPadding ?? const EdgeInsets.symmetric(horizontal: 16, vertical: 8), - tooltipMargin = tooltipMargin ?? const EdgeInsets.only(bottom: 8), + tooltipMargin = tooltipMargin ?? EdgeInsets.zero, tooltipVerticalOffset = tooltipVerticalOffset ?? 16, tooltipHorizontalAlignment = tooltipHorizontalAlignment ?? FLHorizontalAlignment.center, From 1b7ebaf439847db92bd3615dc795aa1210c1aca9 Mon Sep 17 00:00:00 2001 From: Jani Koponen Date: Thu, 23 Nov 2023 09:45:18 +0200 Subject: [PATCH 04/27] Adjust tests based on zero margin and removed textBelowMargin --- .../bar_chart/bar_chart_painter_test.dart | 30 +++++++++---------- 1 file changed, 15 insertions(+), 15 deletions(-) diff --git a/test/chart/bar_chart/bar_chart_painter_test.dart b/test/chart/bar_chart/bar_chart_painter_test.dart index 9695a033c..7ccc8ccc4 100644 --- a/test/chart/bar_chart/bar_chart_painter_test.dart +++ b/test/chart/bar_chart/bar_chart_painter_test.dart @@ -1171,9 +1171,9 @@ void main() { final rrect = result1.captured[0] as RRect; expect(rrect.blRadius, const Radius.circular(8)); expect(rrect.width, 112); - expect(rrect.height, 90); + expect(rrect.height, 86); expect(rrect.left, -22.5); - expect(rrect.top, -106); + expect(rrect.top, -102); final bgTooltipPaint = result1.captured[1] as Paint; expect(bgTooltipPaint.color, const Color(0xf33f33f3)); @@ -1184,9 +1184,9 @@ void main() { expect(rRectBorder.blRadius, const Radius.circular(8)); expect(rRectBorder.width, 112); - expect(rRectBorder.height, 90); + expect(rRectBorder.height, 86); expect(rRectBorder.left, -22.5); - expect(rRectBorder.top, -106); + expect(rRectBorder.top, -102); expect(paintBorder.color, const Color(0xf33f33f3)); expect(paintBorder.strokeWidth, 2); expect(paintBorder.style, PaintingStyle.stroke); @@ -1211,7 +1211,7 @@ void main() { ); final drawOffset = result2.captured[1] as Offset; - expect(drawOffset, const Offset(-6.5, -98)); + expect(drawOffset, const Offset(-6.5, -94)); }); test('test 2', () { @@ -1371,9 +1371,9 @@ void main() { final rrect = result1.captured[0] as RRect; expect(rrect.blRadius, const Radius.circular(8)); expect(rrect.width, 112); - expect(rrect.height, 90); + expect(rrect.height, 86); expect(rrect.left, -80); - expect(rrect.top, 116); + expect(rrect.top, 100); final bgTooltipPaint = result1.captured[1] as Paint; expect(bgTooltipPaint.color, const Color(0xf33f33f3)); @@ -1384,9 +1384,9 @@ void main() { expect(rRectBorder.blRadius, const Radius.circular(8)); expect(rRectBorder.width, 112); - expect(rRectBorder.height, 90); + expect(rRectBorder.height, 86); expect(rRectBorder.left, -80); - expect(rRectBorder.top, 116); + expect(rRectBorder.top, 100); expect(paintBorder.color, const Color(0xf33f33f3)); expect(paintBorder.strokeWidth, 2); expect(paintBorder.style, PaintingStyle.stroke); @@ -1411,7 +1411,7 @@ void main() { ); final drawOffset = result2.captured[1] as Offset; - expect(drawOffset, const Offset(-64, 124)); + expect(drawOffset, const Offset(-64, 108)); }); test('test 3', () { @@ -1546,9 +1546,9 @@ void main() { final rrect = result1.captured[0] as RRect; expect(rrect.blRadius, const Radius.circular(8)); expect(rrect.width, 2636); - expect(rrect.height, 7034.0); + expect(rrect.height, 7030.0); expect(rrect.left, -2436); - expect(rrect.top, -6934.0); + expect(rrect.top, -6930.0); final bgTooltipPaint = result1.captured[1] as Paint; expect(bgTooltipPaint.color, const Color(0xf33f33f3)); @@ -1559,9 +1559,9 @@ void main() { expect(rRectBorder.blRadius, const Radius.circular(8)); expect(rRectBorder.width, 2636); - expect(rRectBorder.height, 7034.0); + expect(rRectBorder.height, 7030.0); expect(rRectBorder.left, -2436); - expect(rRectBorder.top, -6934.0); + expect(rRectBorder.top, -6930.0); expect(paintBorder.color, const Color(0xf33f33f3)); expect(paintBorder.strokeWidth, 2); expect(paintBorder.style, PaintingStyle.stroke); @@ -1573,7 +1573,7 @@ void main() { ..called(1); final drawOffset = result2.captured[1] as Offset; - expect(drawOffset, const Offset(-2420, -6926)); + expect(drawOffset, const Offset(-2420, -6922)); }); }); From 08ab996b2c33badda0edd97e042fdd7fa9fcfd69 Mon Sep 17 00:00:00 2001 From: Jani Koponen Date: Thu, 23 Nov 2023 09:46:07 +0200 Subject: [PATCH 05/27] Adjust default values and fix line chart painter --- lib/src/chart/bar_chart/bar_chart_painter.dart | 2 +- lib/src/chart/line_chart/line_chart_data.dart | 2 +- lib/src/chart/line_chart/line_chart_painter.dart | 9 ++++----- 3 files changed, 6 insertions(+), 7 deletions(-) diff --git a/lib/src/chart/bar_chart/bar_chart_painter.dart b/lib/src/chart/bar_chart/bar_chart_painter.dart index 1d1337bc5..ff49f9d1f 100644 --- a/lib/src/chart/bar_chart/bar_chart_painter.dart +++ b/lib/src/chart/bar_chart/bar_chart_painter.dart @@ -417,7 +417,7 @@ class BarChartPainter extends AxisChartPainter { // ignore: omit_local_variable_types final backgroundRect = Rect.fromLTWH( tooltipLeft, - tooltipTop, + tooltipTop - tooltipData.tooltipPadding.vertical / 2, tooltipWidth, tooltipHeight, ); diff --git a/lib/src/chart/line_chart/line_chart_data.dart b/lib/src/chart/line_chart/line_chart_data.dart index 604295dff..1e176eb58 100644 --- a/lib/src/chart/line_chart/line_chart_data.dart +++ b/lib/src/chart/line_chart/line_chart_data.dart @@ -1038,7 +1038,7 @@ class LineTouchTooltipData with EquatableMixin { this.tooltipRoundedRadius = 4, this.tooltipPadding = const EdgeInsets.symmetric(horizontal: 16, vertical: 8), - this.tooltipMargin = const EdgeInsets.only(bottom: 8), + this.tooltipMargin = EdgeInsets.zero, this.tooltipVerticalOffset = 16, this.tooltipHorizontalAlignment = FLHorizontalAlignment.center, this.tooltipHorizontalOffset = 0, diff --git a/lib/src/chart/line_chart/line_chart_painter.dart b/lib/src/chart/line_chart/line_chart_painter.dart index cf2818348..4143e8ba5 100644 --- a/lib/src/chart/line_chart/line_chart_painter.dart +++ b/lib/src/chart/line_chart/line_chart_painter.dart @@ -988,8 +988,6 @@ class LineChartPainter extends AxisChartPainter { ) { final viewSize = canvasWrapper.size; - const textsBelowPadding = 4; - /// creating TextPainters to calculate the width and height of the tooltip final drawingTextPainters = []; @@ -1038,7 +1036,8 @@ class LineChartPainter extends AxisChartPainter { } sumTextsHeight += tp.height; } - sumTextsHeight += (drawingTextPainters.length - 1) * textsBelowPadding; + sumTextsHeight += + (drawingTextPainters.length - 1) * tooltipData.tooltipPadding.bottom; /// if we have multiple bar lines, /// there are more than one FlCandidate on touch area, @@ -1071,7 +1070,7 @@ class LineChartPainter extends AxisChartPainter { /// draw the background rect with rounded radius final backgroundRect = Rect.fromLTWH( tooltipLeftPosition, - tooltipTopPosition, + tooltipTopPosition - tooltipData.tooltipPadding.vertical / 2, tooltipWidth, tooltipHeight, ); @@ -1206,7 +1205,7 @@ class LineChartPainter extends AxisChartPainter { }, ); topPosSeek += tp.height; - topPosSeek += textsBelowPadding; + topPosSeek += tooltipData.tooltipPadding.bottom; } } From 469fb8fb700755d830834f16d0c2f4c259e4923b Mon Sep 17 00:00:00 2001 From: Jani Koponen Date: Thu, 4 Jan 2024 15:21:06 +0200 Subject: [PATCH 06/27] Add padding and margin extensions for Rect --- lib/src/extensions/rect_extension.dart | 21 +++++++++++++++++++++ 1 file changed, 21 insertions(+) create mode 100644 lib/src/extensions/rect_extension.dart diff --git a/lib/src/extensions/rect_extension.dart b/lib/src/extensions/rect_extension.dart new file mode 100644 index 000000000..2e40e7430 --- /dev/null +++ b/lib/src/extensions/rect_extension.dart @@ -0,0 +1,21 @@ +import 'package:flutter/material.dart'; + +extension RectExtension on Rect { + Rect applyPadding(EdgeInsets padding) { + return Rect.fromLTRB( + left - padding.left, + top - padding.top, + right + padding.right, + bottom + padding.bottom, + ); + } + + Rect applyMargin(EdgeInsets margin) => Rect.fromCenter( + center: Offset( + center.dx + margin.horizontal, + center.dy - margin.vertical, + ), + width: width, + height: height, + ); +} From 6073a8048c0c360b03329c59613b6d363d6f1c50 Mon Sep 17 00:00:00 2001 From: Jani Koponen Date: Thu, 4 Jan 2024 15:21:35 +0200 Subject: [PATCH 07/27] Add tests for RectExtension --- test/extensions/rect_extension_test.dart | 55 ++++++++++++++++++++++++ 1 file changed, 55 insertions(+) create mode 100644 test/extensions/rect_extension_test.dart diff --git a/test/extensions/rect_extension_test.dart b/test/extensions/rect_extension_test.dart new file mode 100644 index 000000000..62da6afbf --- /dev/null +++ b/test/extensions/rect_extension_test.dart @@ -0,0 +1,55 @@ +import 'package:fl_chart/src/extensions/rect_extension.dart'; +import 'package:flutter/widgets.dart'; +import 'package:flutter_test/flutter_test.dart'; + +void main() { + group('RectExtension', () { + group('addPadding', () { + test('should not affect with EdgeInsets.zero', () { + const rect = Rect.fromLTWH(1, 1, 1, 1); + const padding = EdgeInsets.zero; + + expect(rect.applyPadding(padding), rect); + }); + + // Adjust tooltip start heights? + + test('should add correct amount of padding', () { + const rect = Rect.fromLTRB(25, 50, 100, 100); + const padding = EdgeInsets.symmetric(vertical: 16, horizontal: 8); + expect( + rect.applyPadding(padding), + Rect.fromLTRB( + 25 - padding.left, + 50 - padding.top, + 100 + padding.right, + 100 + padding.bottom, + ), + ); + }); + }); + + group('addMargin', () { + test('should not affect with EdgeInsets.zero', () { + const rect = Rect.fromLTWH(1, 1, 1, 1); + const margin = EdgeInsets.zero; + + expect(rect.applyMargin(margin), rect); + }); + + test('should move rect the correct amount', () { + const rect = Rect.fromLTRB(25, 250, 100, 300); + const margin = EdgeInsets.symmetric(vertical: 16, horizontal: 8); + expect( + rect.applyMargin(margin), + Rect.fromLTRB( + 25 + margin.horizontal, + 250 - margin.vertical, + 100 + margin.horizontal, + 300 - margin.vertical, + ), + ); + }); + }); + }); +} From 813d88124122626c30a6517defb627cbf05ba0fa Mon Sep 17 00:00:00 2001 From: Jani Koponen Date: Thu, 4 Jan 2024 15:22:28 +0200 Subject: [PATCH 08/27] Add padding and margin to painter --- .../chart/bar_chart/bar_chart_painter.dart | 43 ++++--------------- .../chart/line_chart/line_chart_painter.dart | 30 ++++--------- 2 files changed, 16 insertions(+), 57 deletions(-) diff --git a/lib/src/chart/bar_chart/bar_chart_painter.dart b/lib/src/chart/bar_chart/bar_chart_painter.dart index ff49f9d1f..0c6d49ad3 100644 --- a/lib/src/chart/bar_chart/bar_chart_painter.dart +++ b/lib/src/chart/bar_chart/bar_chart_painter.dart @@ -7,6 +7,7 @@ import 'package:fl_chart/src/chart/base/base_chart/base_chart_painter.dart'; import 'package:fl_chart/src/extensions/bar_chart_data_extension.dart'; import 'package:fl_chart/src/extensions/paint_extension.dart'; import 'package:fl_chart/src/extensions/path_extension.dart'; +import 'package:fl_chart/src/extensions/rect_extension.dart'; import 'package:fl_chart/src/extensions/rrect_extension.dart'; import 'package:fl_chart/src/utils/canvas_wrapper.dart'; import 'package:fl_chart/src/utils/utils.dart'; @@ -371,16 +372,6 @@ class BarChartPainter extends AxisChartPainter { /// creating TextPainters to calculate the width and height of the tooltip final drawingTextPainter = tp; - /// biggerWidth - /// some texts maybe larger, then we should - /// draw the tooltip' width as wide as biggerWidth - /// - /// sumTextsHeight - /// sum up all Texts height, then we should - /// draw the tooltip's height as tall as sumTextsHeight - final textWidth = drawingTextPainter.width; - final textHeight = drawingTextPainter.height; - /// if we have multiple bar lines, /// there are more than one FlCandidate on touch area, /// we should get the most top FlSpot Offset to draw the tooltip on top of it @@ -393,9 +384,8 @@ class BarChartPainter extends AxisChartPainter { groupPositions[barGroupIndex].barsX[barRodIndex], getPixelY(showOnRodData.fromY, viewSize, holder), ); - - final tooltipWidth = textWidth + tooltipData.tooltipPadding.horizontal; - final tooltipHeight = textHeight + tooltipData.tooltipPadding.vertical; + final tooltipWidth = drawingTextPainter.width; + final tooltipHeight = drawingTextPainter.height; final barTopY = min(barToYPixel.dy, barFromYPixel.dy); final barBottomY = max(barToYPixel.dy, barFromYPixel.dy); @@ -415,31 +405,14 @@ class BarChartPainter extends AxisChartPainter { /// draw the background rect with rounded radius // ignore: omit_local_variable_types - final backgroundRect = Rect.fromLTWH( + var rect = Rect.fromLTWH( tooltipLeft, - tooltipTop - tooltipData.tooltipPadding.vertical / 2, + tooltipTop, tooltipWidth, tooltipHeight, - ); - - /// Apply padding to background rect - var rect = Rect.fromLTRB( - backgroundRect.left - tooltipData.tooltipPadding.left, - backgroundRect.top - tooltipData.tooltipPadding.top, - backgroundRect.right + tooltipData.tooltipPadding.right, - backgroundRect.bottom + tooltipData.tooltipPadding.bottom, - ); - - /// Apply margin to background rect - /// Since margin is meant for outside the object, we can mimic it by shifting the object center - rect = Rect.fromCenter( - center: Offset( - rect.center.dx + tooltipData.tooltipMargin.horizontal, - rect.center.dy - tooltipData.tooltipMargin.vertical, - ), - width: rect.width, - height: rect.height, - ); + ) + .applyPadding(tooltipData.tooltipPadding) + .applyMargin(tooltipData.tooltipMargin); if (tooltipData.fitInsideHorizontally) { if (rect.left < 0) { diff --git a/lib/src/chart/line_chart/line_chart_painter.dart b/lib/src/chart/line_chart/line_chart_painter.dart index 4143e8ba5..dcc0005f9 100644 --- a/lib/src/chart/line_chart/line_chart_painter.dart +++ b/lib/src/chart/line_chart/line_chart_painter.dart @@ -6,6 +6,7 @@ import 'package:fl_chart/src/chart/base/axis_chart/axis_chart_painter.dart'; import 'package:fl_chart/src/chart/base/base_chart/base_chart_painter.dart'; import 'package:fl_chart/src/extensions/paint_extension.dart'; import 'package:fl_chart/src/extensions/path_extension.dart'; +import 'package:fl_chart/src/extensions/rect_extension.dart'; import 'package:fl_chart/src/extensions/text_align_extension.dart'; import 'package:fl_chart/src/utils/canvas_wrapper.dart'; import 'package:fl_chart/src/utils/utils.dart'; @@ -1036,8 +1037,10 @@ class LineChartPainter extends AxisChartPainter { } sumTextsHeight += tp.height; } + print(sumTextsHeight); sumTextsHeight += (drawingTextPainters.length - 1) * tooltipData.tooltipPadding.bottom; + print(sumTextsHeight); /// if we have multiple bar lines, /// there are more than one FlCandidate on touch area, @@ -1068,31 +1071,14 @@ class LineChartPainter extends AxisChartPainter { ); /// draw the background rect with rounded radius - final backgroundRect = Rect.fromLTWH( + var rect = Rect.fromLTWH( tooltipLeftPosition, - tooltipTopPosition - tooltipData.tooltipPadding.vertical / 2, + tooltipTopPosition, tooltipWidth, tooltipHeight, - ); - - /// Apply padding to background rect - var rect = Rect.fromLTRB( - backgroundRect.left - tooltipData.tooltipPadding.left, - backgroundRect.top - tooltipData.tooltipPadding.top, - backgroundRect.right + tooltipData.tooltipPadding.right, - backgroundRect.bottom + tooltipData.tooltipPadding.bottom, - ); - - /// Apply margin to background rect - /// Since margin affects outside area of the object, we can mimic it by shifting the object center - rect = Rect.fromCenter( - center: Offset( - rect.center.dx + tooltipData.tooltipMargin.horizontal, - rect.center.dy - tooltipData.tooltipMargin.vertical, - ), - width: rect.width, - height: rect.height, - ); + ) + .applyPadding(tooltipData.tooltipPadding) + .applyMargin(tooltipData.tooltipMargin); if (tooltipData.fitInsideHorizontally) { if (rect.left < 0) { From b7835728a281c661b31ebafbf930af9559cd3aaf Mon Sep 17 00:00:00 2001 From: Jani Koponen Date: Thu, 4 Jan 2024 15:22:36 +0200 Subject: [PATCH 09/27] Remove bottom margin --- test/chart/data_pool.dart | 1 - 1 file changed, 1 deletion(-) diff --git a/test/chart/data_pool.dart b/test/chart/data_pool.dart index 15878f51e..6781b0dc3 100644 --- a/test/chart/data_pool.dart +++ b/test/chart/data_pool.dart @@ -2231,7 +2231,6 @@ ScatterTooltipItem? scatterChartGetTooltipItems(ScatterSpot spots) { return ScatterTooltipItem( 'check', textStyle: const TextStyle(color: Colors.blue), - bottomMargin: 23, ); } From 9712d69ac3942e6210d3f3157a7737f1ae3467a6 Mon Sep 17 00:00:00 2001 From: Jani Koponen Date: Thu, 4 Jan 2024 15:24:05 +0200 Subject: [PATCH 10/27] Move margin to tooltipdata and rename to vertical offset --- .../chart/scatter_chart/scatter_chart_data.dart | 17 ++++++++--------- 1 file changed, 8 insertions(+), 9 deletions(-) diff --git a/lib/src/chart/scatter_chart/scatter_chart_data.dart b/lib/src/chart/scatter_chart/scatter_chart_data.dart index 14966cea1..d5cfc6eb4 100644 --- a/lib/src/chart/scatter_chart/scatter_chart_data.dart +++ b/lib/src/chart/scatter_chart/scatter_chart_data.dart @@ -405,6 +405,7 @@ class ScatterTouchTooltipData with EquatableMixin { EdgeInsets? tooltipPadding, EdgeInsets? tooltipMargin, FLHorizontalAlignment? tooltipHorizontalAlignment, + double? tooltipVerticalOffset, double? tooltipHorizontalOffset, double? maxContentWidth, GetScatterTooltipItems? getTooltipItems, @@ -414,11 +415,13 @@ class ScatterTouchTooltipData with EquatableMixin { BorderSide? tooltipBorder, }) : tooltipBgColor = tooltipBgColor ?? Colors.blueGrey.darken(15), tooltipRoundedRadius = tooltipRoundedRadius ?? 4, - tooltipPadding = tooltipPadding ?? const EdgeInsets.all(6), + tooltipPadding = tooltipPadding ?? + const EdgeInsets.symmetric(horizontal: 16, vertical: 8), tooltipMargin = tooltipMargin ?? EdgeInsets.zero, tooltipHorizontalAlignment = tooltipHorizontalAlignment ?? FLHorizontalAlignment.center, tooltipHorizontalOffset = tooltipHorizontalOffset ?? 0, + tooltipVerticalOffset = tooltipVerticalOffset ?? 0, maxContentWidth = maxContentWidth ?? 120, getTooltipItems = getTooltipItems ?? defaultScatterTooltipItem, fitInsideHorizontally = fitInsideHorizontally ?? false, @@ -445,6 +448,9 @@ class ScatterTouchTooltipData with EquatableMixin { /// Applies horizontal offset for showing tooltip, default is zero. final double tooltipHorizontalOffset; + /// Applies vertical offset for showing tooltip, default is zero. + final double tooltipVerticalOffset; + /// Restricts the tooltip's width. final double maxContentWidth; @@ -550,12 +556,10 @@ class ScatterTooltipItem with EquatableMixin { ScatterTooltipItem( this.text, { this.textStyle, - double? bottomMargin, TextAlign? textAlign, TextDirection? textDirection, this.children, - }) : bottomMargin = bottomMargin ?? 8, - textAlign = textAlign ?? TextAlign.center, + }) : textAlign = textAlign ?? TextAlign.center, textDirection = textDirection ?? TextDirection.ltr; /// Showing text. @@ -564,9 +568,6 @@ class ScatterTooltipItem with EquatableMixin { /// Style of showing text. final TextStyle? textStyle; - /// Defines bottom space from spot. - final double bottomMargin; - /// TextAlign of the showing content. final TextAlign textAlign; @@ -581,7 +582,6 @@ class ScatterTooltipItem with EquatableMixin { List get props => [ text, textStyle, - bottomMargin, textAlign, textDirection, children, @@ -600,7 +600,6 @@ class ScatterTooltipItem with EquatableMixin { return ScatterTooltipItem( text ?? this.text, textStyle: textStyle ?? this.textStyle, - bottomMargin: bottomMargin ?? this.bottomMargin, textAlign: textAlign ?? this.textAlign, textDirection: textDirection ?? this.textDirection, children: children ?? this.children, From 54aadc587e4e936c93d32dcaae7aab06a4520023 Mon Sep 17 00:00:00 2001 From: Jani Koponen Date: Thu, 4 Jan 2024 15:24:29 +0200 Subject: [PATCH 11/27] Add padding and margin to scatter tooltip painter --- .../scatter_chart/scatter_chart_painter.dart | 34 +++++-------------- 1 file changed, 8 insertions(+), 26 deletions(-) diff --git a/lib/src/chart/scatter_chart/scatter_chart_painter.dart b/lib/src/chart/scatter_chart/scatter_chart_painter.dart index 27b05eeee..3b8193702 100644 --- a/lib/src/chart/scatter_chart/scatter_chart_painter.dart +++ b/lib/src/chart/scatter_chart/scatter_chart_painter.dart @@ -1,6 +1,7 @@ import 'package:fl_chart/fl_chart.dart'; import 'package:fl_chart/src/chart/base/axis_chart/axis_chart_painter.dart'; import 'package:fl_chart/src/chart/base/base_chart/base_chart_painter.dart'; +import 'package:fl_chart/src/extensions/rect_extension.dart'; import 'package:fl_chart/src/utils/canvas_wrapper.dart'; import 'package:fl_chart/src/utils/utils.dart'; import 'package:flutter/material.dart'; @@ -238,8 +239,8 @@ class ScatterChartPainter extends AxisChartPainter { getPixelY(showOnSpot.y, viewSize, holder), ); - final tooltipWidth = width + tooltipData.tooltipPadding.horizontal; - final tooltipHeight = height + tooltipData.tooltipPadding.vertical; + final tooltipWidth = width; + final tooltipHeight = height; final tooltipLeftPosition = getTooltipLeft( mostTopOffset.dx, @@ -250,36 +251,17 @@ class ScatterChartPainter extends AxisChartPainter { ); /// draw the background rect with rounded radius - final backgroundRect = Rect.fromLTWH( + var rect = Rect.fromLTWH( tooltipLeftPosition, mostTopOffset.dy - tooltipHeight - (showOnSpot.size.height / 2) - - tooltipItem.bottomMargin, + tooltipData.tooltipVerticalOffset, tooltipWidth, tooltipHeight, - ); - - /// Apply padding to background rect - var rect = Rect.fromLTRB( - backgroundRect.left - tooltipData.tooltipPadding.left, - backgroundRect.top - tooltipData.tooltipPadding.top, - backgroundRect.right + tooltipData.tooltipPadding.right, - backgroundRect.bottom + - tooltipData.tooltipPadding.bottom - - tooltipItem.bottomMargin, - ); - - /// Apply margin to background rect - /// Since margin affects outside area of the object, we can mimic it by shifting the object center - rect = Rect.fromCenter( - center: Offset( - rect.center.dx + tooltipData.tooltipMargin.horizontal, - rect.center.dy - tooltipData.tooltipMargin.vertical, - ), - width: rect.width, - height: rect.height, - ); + ) + .applyPadding(tooltipData.tooltipPadding) + .applyMargin(tooltipData.tooltipMargin); if (tooltipData.fitInsideHorizontally) { if (rect.left < 0) { From c7d3740001c576c1f111d222a2e9c23ef2a388fb Mon Sep 17 00:00:00 2001 From: Jani Koponen Date: Thu, 4 Jan 2024 15:24:40 +0200 Subject: [PATCH 12/27] Remove bottom margin from tests --- test/chart/scatter_chart/scatter_chart_data_test.dart | 5 ----- 1 file changed, 5 deletions(-) diff --git a/test/chart/scatter_chart/scatter_chart_data_test.dart b/test/chart/scatter_chart/scatter_chart_data_test.dart index 671468402..59f32c3d1 100644 --- a/test/chart/scatter_chart/scatter_chart_data_test.dart +++ b/test/chart/scatter_chart/scatter_chart_data_test.dart @@ -452,33 +452,28 @@ void main() { final sample1 = ScatterTooltipItem( 'aa', textStyle: const TextStyle(color: Colors.red), - bottomMargin: 23, ); final sample2 = ScatterTooltipItem( 'aa', textStyle: const TextStyle(color: Colors.red), - bottomMargin: 23, ); expect(sample1 == sample2, true); var changed = ScatterTooltipItem( 'a3a', textStyle: const TextStyle(color: Colors.red), - bottomMargin: 23, ); expect(sample1 == changed, false); changed = ScatterTooltipItem( 'aa', textStyle: const TextStyle(color: Colors.green), - bottomMargin: 23, ); expect(sample1 == changed, false); changed = ScatterTooltipItem( 'aa', textStyle: const TextStyle(color: Colors.red), - bottomMargin: 0, ); expect(sample1 == changed, false); }); From 4e925187b5b9cc0cb2e025f6871990856f2f5046 Mon Sep 17 00:00:00 2001 From: Jani Koponen Date: Thu, 4 Jan 2024 15:24:52 +0200 Subject: [PATCH 13/27] Adjust examples --- example/lib/presentation/samples/bar/bar_chart_sample1.dart | 2 +- example/lib/presentation/samples/bar/bar_chart_sample3.dart | 2 +- example/lib/presentation/samples/bar/bar_chart_sample7.dart | 2 +- .../lib/presentation/samples/scatter/scatter_chart_sample2.dart | 2 +- 4 files changed, 4 insertions(+), 4 deletions(-) diff --git a/example/lib/presentation/samples/bar/bar_chart_sample1.dart b/example/lib/presentation/samples/bar/bar_chart_sample1.dart index a71f5f04a..28f7f9b0b 100644 --- a/example/lib/presentation/samples/bar/bar_chart_sample1.dart +++ b/example/lib/presentation/samples/bar/bar_chart_sample1.dart @@ -164,7 +164,7 @@ class BarChartSample1State extends State { touchTooltipData: BarTouchTooltipData( tooltipBgColor: Colors.blueGrey, tooltipHorizontalAlignment: FLHorizontalAlignment.right, - tooltipMargin: -10, + tooltipVerticalOffset: -10, getTooltipItem: (group, groupIndex, rod, rodIndex) { String weekDay; switch (group.x) { diff --git a/example/lib/presentation/samples/bar/bar_chart_sample3.dart b/example/lib/presentation/samples/bar/bar_chart_sample3.dart index 3db1cbe79..10576579b 100644 --- a/example/lib/presentation/samples/bar/bar_chart_sample3.dart +++ b/example/lib/presentation/samples/bar/bar_chart_sample3.dart @@ -26,7 +26,7 @@ class _BarChart extends StatelessWidget { touchTooltipData: BarTouchTooltipData( tooltipBgColor: Colors.transparent, tooltipPadding: EdgeInsets.zero, - tooltipMargin: 8, + tooltipVerticalOffset: 8, getTooltipItem: ( BarChartGroupData group, int groupIndex, diff --git a/example/lib/presentation/samples/bar/bar_chart_sample7.dart b/example/lib/presentation/samples/bar/bar_chart_sample7.dart index 03b539360..f59c1788d 100644 --- a/example/lib/presentation/samples/bar/bar_chart_sample7.dart +++ b/example/lib/presentation/samples/bar/bar_chart_sample7.dart @@ -123,7 +123,7 @@ class _BarChartSample7State extends State { handleBuiltInTouches: false, touchTooltipData: BarTouchTooltipData( tooltipBgColor: Colors.transparent, - tooltipMargin: 0, + tooltipVerticalOffset: 0, getTooltipItem: ( BarChartGroupData group, int groupIndex, diff --git a/example/lib/presentation/samples/scatter/scatter_chart_sample2.dart b/example/lib/presentation/samples/scatter/scatter_chart_sample2.dart index 0a1db8f5c..78e3b2bb1 100644 --- a/example/lib/presentation/samples/scatter/scatter_chart_sample2.dart +++ b/example/lib/presentation/samples/scatter/scatter_chart_sample2.dart @@ -126,6 +126,7 @@ class _ScatterChartSample2State extends State { : SystemMouseCursors.click; }, touchTooltipData: ScatterTouchTooltipData( + tooltipVerticalOffset: 10, tooltipBgColor: Colors.black, getTooltipItems: (ScatterSpot touchedBarSpot) { return ScatterTooltipItem( @@ -135,7 +136,6 @@ class _ScatterChartSample2State extends State { color: Colors.grey[100], fontStyle: FontStyle.italic, ), - bottomMargin: 10, children: [ TextSpan( text: '${touchedBarSpot.x.toInt()} \n', From 4e305781c96ffbf347eb0291424aeec2451bc7cc Mon Sep 17 00:00:00 2001 From: Jani Koponen Date: Thu, 4 Jan 2024 19:24:09 +0200 Subject: [PATCH 14/27] Fix tooltip vertical position and right alignment --- lib/src/chart/line_chart/line_chart_painter.dart | 16 +++++++++------- 1 file changed, 9 insertions(+), 7 deletions(-) diff --git a/lib/src/chart/line_chart/line_chart_painter.dart b/lib/src/chart/line_chart/line_chart_painter.dart index dcc0005f9..e9700a356 100644 --- a/lib/src/chart/line_chart/line_chart_painter.dart +++ b/lib/src/chart/line_chart/line_chart_painter.dart @@ -1037,10 +1037,8 @@ class LineChartPainter extends AxisChartPainter { } sumTextsHeight += tp.height; } - print(sumTextsHeight); sumTextsHeight += (drawingTextPainters.length - 1) * tooltipData.tooltipPadding.bottom; - print(sumTextsHeight); /// if we have multiple bar lines, /// there are more than one FlCandidate on touch area, @@ -1055,11 +1053,15 @@ class LineChartPainter extends AxisChartPainter { double tooltipTopPosition; if (tooltipData.showOnTopOfTheChartBoxArea) { - tooltipTopPosition = - 0 - tooltipHeight - tooltipData.tooltipVerticalOffset; + tooltipTopPosition = 0 - + tooltipHeight - + tooltipData.tooltipVerticalOffset - + (tooltipData.tooltipPadding.vertical / 2); } else { - tooltipTopPosition = - mostTopOffset.dy - tooltipHeight - tooltipData.tooltipVerticalOffset; + tooltipTopPosition = mostTopOffset.dy - + tooltipHeight - + tooltipData.tooltipVerticalOffset - + (tooltipData.tooltipPadding.vertical / 2); } final tooltipLeftPosition = getTooltipLeft( @@ -1172,7 +1174,7 @@ class LineChartPainter extends AxisChartPainter { final xOffset = switch (align) { HorizontalAlignment.left => rect.left + tooltipData.tooltipPadding.left, HorizontalAlignment.right => - rect.right - tooltipData.tooltipMargin.right - tp.width, + rect.right - tp.width - tooltipData.tooltipPadding.right, _ => rect.center.dx - (tp.width / 2), }; From a461451c6f2f248eb2decc383605231c3bd7f374 Mon Sep 17 00:00:00 2001 From: Jani Koponen Date: Thu, 4 Jan 2024 19:24:36 +0200 Subject: [PATCH 15/27] Fix tooltip vertical position --- lib/src/chart/bar_chart/bar_chart_painter.dart | 9 +++++++-- lib/src/chart/scatter_chart/scatter_chart_painter.dart | 3 ++- 2 files changed, 9 insertions(+), 3 deletions(-) diff --git a/lib/src/chart/bar_chart/bar_chart_painter.dart b/lib/src/chart/bar_chart/bar_chart_painter.dart index 0c6d49ad3..3e59eaccf 100644 --- a/lib/src/chart/bar_chart/bar_chart_painter.dart +++ b/lib/src/chart/bar_chart/bar_chart_painter.dart @@ -393,8 +393,13 @@ class BarChartPainter extends AxisChartPainter { (tooltipData.direction == TooltipDirection.auto && showOnRodData.isUpward()); final tooltipTop = drawTooltipOnTop - ? barTopY - tooltipHeight - tooltipData.tooltipVerticalOffset - : barBottomY + tooltipData.tooltipVerticalOffset; + ? barTopY - + tooltipHeight - + tooltipData.tooltipVerticalOffset - + (tooltipData.tooltipPadding.vertical / 2) + : barBottomY + + tooltipData.tooltipVerticalOffset - + (tooltipData.tooltipPadding.vertical / 2); final tooltipLeft = getTooltipLeft( barToYPixel.dx, tooltipWidth, diff --git a/lib/src/chart/scatter_chart/scatter_chart_painter.dart b/lib/src/chart/scatter_chart/scatter_chart_painter.dart index 3b8193702..21a769a46 100644 --- a/lib/src/chart/scatter_chart/scatter_chart_painter.dart +++ b/lib/src/chart/scatter_chart/scatter_chart_painter.dart @@ -256,7 +256,8 @@ class ScatterChartPainter extends AxisChartPainter { mostTopOffset.dy - tooltipHeight - (showOnSpot.size.height / 2) - - tooltipData.tooltipVerticalOffset, + tooltipData.tooltipVerticalOffset - + (tooltipData.tooltipPadding.vertical / 2), tooltipWidth, tooltipHeight, ) From be5b7456a0124c021f581aec255a34d17cf11d34 Mon Sep 17 00:00:00 2001 From: Jani Koponen Date: Thu, 4 Jan 2024 19:24:45 +0200 Subject: [PATCH 16/27] Fix equality tests --- test/chart/scatter_chart/scatter_chart_data_test.dart | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/test/chart/scatter_chart/scatter_chart_data_test.dart b/test/chart/scatter_chart/scatter_chart_data_test.dart index 59f32c3d1..6f8b734cb 100644 --- a/test/chart/scatter_chart/scatter_chart_data_test.dart +++ b/test/chart/scatter_chart/scatter_chart_data_test.dart @@ -473,7 +473,7 @@ void main() { changed = ScatterTooltipItem( 'aa', - textStyle: const TextStyle(color: Colors.red), + textStyle: const TextStyle(color: Colors.red, fontSize: 11), ); expect(sample1 == changed, false); }); From 062d9ba44c17731f332dec98b06c4d6b1ad49a30 Mon Sep 17 00:00:00 2001 From: Jani Koponen Date: Thu, 4 Jan 2024 19:25:06 +0200 Subject: [PATCH 17/27] Update documentation --- lib/src/chart/bar_chart/bar_chart_data.dart | 9 +++++---- lib/src/chart/line_chart/line_chart_data.dart | 9 +++++---- .../chart/scatter_chart/scatter_chart_data.dart | 15 +++++++++++---- 3 files changed, 21 insertions(+), 12 deletions(-) diff --git a/lib/src/chart/bar_chart/bar_chart_data.dart b/lib/src/chart/bar_chart/bar_chart_data.dart index 987149a5e..1aab10179 100644 --- a/lib/src/chart/bar_chart/bar_chart_data.dart +++ b/lib/src/chart/bar_chart/bar_chart_data.dart @@ -692,6 +692,7 @@ class BarTouchTooltipData with EquatableMixin { /// If you want to have tooltip padding, fill [tooltipPadding], /// If you want to have tooltip margin, fill [tooltipMargin]. /// If you want to adjust tooltip vertical position, set [tooltipVerticalOffset] + /// If you want to adjust tooltip horizontal position, set [tooltipHorizontalOffset] /// Content of the tooltip will provide using [getTooltipItem] callback, you can override it /// and pass your custom data to show in the tooltip. /// You can restrict the tooltip's width using [maxContentWidth]. @@ -703,8 +704,8 @@ class BarTouchTooltipData with EquatableMixin { double? tooltipRoundedRadius, EdgeInsets? tooltipPadding, EdgeInsets? tooltipMargin, - double? tooltipVerticalOffset, FLHorizontalAlignment? tooltipHorizontalAlignment, + double? tooltipVerticalOffset, double? tooltipHorizontalOffset, double? maxContentWidth, GetBarTooltipItem? getTooltipItem, @@ -743,15 +744,15 @@ class BarTouchTooltipData with EquatableMixin { /// Applies a margin for content final EdgeInsets tooltipMargin; - /// Adds a offset for tooltip vertical position (offset is applied to bottom of the tooltip) for showing tooltip on top of rods. - final double tooltipVerticalOffset; - /// Controls showing tooltip on left side, right side or center aligned with rod, default is center final FLHorizontalAlignment tooltipHorizontalAlignment; /// Applies horizontal offset for showing tooltip, default is zero. final double tooltipHorizontalOffset; + /// Adds a offset for tooltip vertical position (offset is applied to bottom of the tooltip) for showing tooltip on top of rods. + final double tooltipVerticalOffset; + /// Restricts the tooltip's width. final double maxContentWidth; diff --git a/lib/src/chart/line_chart/line_chart_data.dart b/lib/src/chart/line_chart/line_chart_data.dart index 1e176eb58..19222a8e7 100644 --- a/lib/src/chart/line_chart/line_chart_data.dart +++ b/lib/src/chart/line_chart/line_chart_data.dart @@ -1027,6 +1027,7 @@ class LineTouchTooltipData with EquatableMixin { /// If you want to have tooltip padding, fill [tooltipPadding], /// If you want to have tooltip margin, fill [tooltipMargin]. /// If you want to adjust tooltip vertical position, set [tooltipVerticalOffset] + /// If you want to adjust tooltip horizontal position, set [tooltipHorizontalOffset] /// Content of the tooltip will provide using [getTooltipItems] callback, you can override it /// and pass your custom data to show in the tooltip. /// You can restrict the tooltip's width using [maxContentWidth]. @@ -1039,8 +1040,8 @@ class LineTouchTooltipData with EquatableMixin { this.tooltipPadding = const EdgeInsets.symmetric(horizontal: 16, vertical: 8), this.tooltipMargin = EdgeInsets.zero, - this.tooltipVerticalOffset = 16, this.tooltipHorizontalAlignment = FLHorizontalAlignment.center, + this.tooltipVerticalOffset = 16, this.tooltipHorizontalOffset = 0, this.maxContentWidth = 120, this.getTooltipItems = defaultLineTooltipItem, @@ -1063,15 +1064,15 @@ class LineTouchTooltipData with EquatableMixin { /// Applies a margin for content final EdgeInsets tooltipMargin; - /// Adds a offset for tooltip vertical position (offset is applied to bottom of the tooltip) for showing tooltip on top of rods. - final double tooltipVerticalOffset; - /// Controls showing tooltip on left side, right side or center aligned with spot, default is center final FLHorizontalAlignment tooltipHorizontalAlignment; /// Applies horizontal offset for showing tooltip, default is zero. final double tooltipHorizontalOffset; + /// Adds a offset for tooltip vertical position (offset is applied to bottom of the tooltip) for showing tooltip on top of rods. + final double tooltipVerticalOffset; + /// Restricts the tooltip's width. final double maxContentWidth; diff --git a/lib/src/chart/scatter_chart/scatter_chart_data.dart b/lib/src/chart/scatter_chart/scatter_chart_data.dart index d5cfc6eb4..9b8e20033 100644 --- a/lib/src/chart/scatter_chart/scatter_chart_data.dart +++ b/lib/src/chart/scatter_chart/scatter_chart_data.dart @@ -392,7 +392,10 @@ class ScatterTouchTooltipData with EquatableMixin { /// otherwise you can show it manually using [ScatterChartData.showingTooltipIndicators]. /// Tooltip shows on top of spots, with [tooltipBgColor] as a background color, /// and you can set corner radius using [tooltipRoundedRadius]. - /// If you want to have a padding inside the tooltip, fill [tooltipPadding]. + /// If you want to have tooltip padding, fill [tooltipPadding], + /// If you want to have tooltip margin, fill [tooltipMargin]. + /// If you want to adjust tooltip vertical position, set [tooltipVerticalOffset] + /// If you want to adjust tooltip horizontal position, set [tooltipHorizontalOffset] /// Content of the tooltip will provide using [getTooltipItems] callback, you can override it /// and pass your custom data to show in the tooltip. /// You can restrict the tooltip's width using [maxContentWidth]. @@ -421,7 +424,7 @@ class ScatterTouchTooltipData with EquatableMixin { tooltipHorizontalAlignment = tooltipHorizontalAlignment ?? FLHorizontalAlignment.center, tooltipHorizontalOffset = tooltipHorizontalOffset ?? 0, - tooltipVerticalOffset = tooltipVerticalOffset ?? 0, + tooltipVerticalOffset = tooltipVerticalOffset ?? 8, maxContentWidth = maxContentWidth ?? 120, getTooltipItems = getTooltipItems ?? defaultScatterTooltipItem, fitInsideHorizontally = fitInsideHorizontally ?? false, @@ -478,6 +481,7 @@ class ScatterTouchTooltipData with EquatableMixin { tooltipPadding, tooltipHorizontalAlignment, tooltipHorizontalOffset, + tooltipVerticalOffset, maxContentWidth, getTooltipItems, fitInsideHorizontally, @@ -491,8 +495,10 @@ class ScatterTouchTooltipData with EquatableMixin { ScatterTouchTooltipData copyWith({ Color? tooltipBgColor, double? tooltipRoundedRadius, + EdgeInsets? tooltipMargin, EdgeInsets? tooltipPadding, FLHorizontalAlignment? tooltipHorizontalAlignment, + double? tooltipVerticalOffset, double? tooltipHorizontalOffset, double? maxContentWidth, GetScatterTooltipItems? getTooltipItems, @@ -504,11 +510,14 @@ class ScatterTouchTooltipData with EquatableMixin { return ScatterTouchTooltipData( tooltipBgColor: tooltipBgColor ?? this.tooltipBgColor, tooltipRoundedRadius: tooltipRoundedRadius ?? this.tooltipRoundedRadius, + tooltipMargin: tooltipMargin ?? this.tooltipMargin, tooltipPadding: tooltipPadding ?? this.tooltipPadding, tooltipHorizontalAlignment: tooltipHorizontalAlignment ?? this.tooltipHorizontalAlignment, tooltipHorizontalOffset: tooltipHorizontalOffset ?? this.tooltipHorizontalOffset, + tooltipVerticalOffset: + tooltipVerticalOffset ?? this.tooltipVerticalOffset, maxContentWidth: maxContentWidth ?? this.maxContentWidth, getTooltipItems: getTooltipItems ?? this.getTooltipItems, fitInsideHorizontally: @@ -552,7 +561,6 @@ ScatterTooltipItem? defaultScatterTooltipItem(ScatterSpot touchedSpot) { /// Holds data of showing each item in the tooltip popup. class ScatterTooltipItem with EquatableMixin { /// Shows a [text] with [textStyle], [textDirection], and optional [children] in the tooltip popup, - /// [bottomMargin] is the bottom space from spot. ScatterTooltipItem( this.text, { this.textStyle, @@ -592,7 +600,6 @@ class ScatterTooltipItem with EquatableMixin { ScatterTooltipItem copyWith({ String? text, TextStyle? textStyle, - double? bottomMargin, TextAlign? textAlign, TextDirection? textDirection, List? children, From 3805acb4dda514656962f233eb63f82cf2351861 Mon Sep 17 00:00:00 2001 From: Jani Koponen Date: Thu, 4 Jan 2024 19:39:16 +0200 Subject: [PATCH 18/27] Update CHANGELOG --- CHANGELOG.md | 31 +++++++++++++++++++++++++++++++ 1 file changed, 31 insertions(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index b175315be..a61e3f6dc 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,34 @@ +## newVersion + +* **IMPROVEMENT** (by @k0psutin) Add `tooltipPadding` to BarTouchTooltipData, LineTouchTooltipData and ScatterTouchTooltipData, #824 +* **BREAKING** (by @k0psutin) Update `tooltipMargin` to accept EdgeInsets, #824 +* **BREAKING** (by @kopsutin) Add property `tooltipVerticalOffset` to BarTouchTooltipData, LineTouchTooltipData and ScatterTooltipItem to replace `tooltipMargin`, #824 +```dart +/// Migration guide: +/// Old way: +BarTouchTooltipData( + tooltipMargin: -10, +) + +/// New way: +BarTouchTooltipData( + tooltipVerticalOffset: -10, +) +``` +* **BREAKING** (by @k0psutin) Remove `tooltipMargin` property from ScatterTooltipItem, #824 +```dart +/// Migration guide: +/// Old way: +ScatterTooltipItem( + tooltipMargin: 10, +) + +/// New way: +ScatterTouchTooltipData( + tooltipVerticalOffset: 10, +) +``` + ## 0.66.2 * **BUGFIX** (by @stwarwas) Remove dart.io to fix web platform issue, #1577 From fd7b6fb04ec7a43e49d05256a6aa55698f03a88f Mon Sep 17 00:00:00 2001 From: Jani Koponen Date: Wed, 31 Jan 2024 20:12:39 +0200 Subject: [PATCH 19/27] Add tests and fix rect_extension --- lib/src/extensions/rect_extension.dart | 4 +- .../line_chart/line_chart_painter_test.dart | 224 ++++++++++++++++++ test/extensions/rect_extension_test.dart | 13 +- 3 files changed, 232 insertions(+), 9 deletions(-) diff --git a/lib/src/extensions/rect_extension.dart b/lib/src/extensions/rect_extension.dart index 2e40e7430..3df2f4876 100644 --- a/lib/src/extensions/rect_extension.dart +++ b/lib/src/extensions/rect_extension.dart @@ -12,8 +12,8 @@ extension RectExtension on Rect { Rect applyMargin(EdgeInsets margin) => Rect.fromCenter( center: Offset( - center.dx + margin.horizontal, - center.dy - margin.vertical, + center.dx - margin.right + margin.left, + center.dy - margin.bottom + margin.top, ), width: width, height: height, diff --git a/test/chart/line_chart/line_chart_painter_test.dart b/test/chart/line_chart/line_chart_painter_test.dart index 2180bbaf3..2e8ef8731 100644 --- a/test/chart/line_chart/line_chart_painter_test.dart +++ b/test/chart/line_chart/line_chart_painter_test.dart @@ -2626,6 +2626,230 @@ void main() { expect((textPainter.text as TextSpan?)!.style, textStyle1); expect(drawOffset, const Offset(22, 52)); }); + + test('test 4 - should move tooltip 12 pixels to the right', () { + const viewSize = Size(100, 100); + + final barData = LineChartBarData( + spots: const [ + FlSpot(1, 1), + FlSpot(2, 2), + FlSpot(3, 3), + FlSpot(4, 4), + FlSpot.nullSpot, + FlSpot(5, 5), + ], + ); + + final tooltipData = LineTouchTooltipData( + tooltipBgColor: const Color(0x11111111), + tooltipRoundedRadius: 12, + rotateAngle: 43, + maxContentWidth: 100, + tooltipVerticalOffset: 12, + tooltipHorizontalAlignment: FLHorizontalAlignment.right, + tooltipPadding: const EdgeInsets.all(12), + tooltipMargin: const EdgeInsets.only(left: 12), + fitInsideVertically: true, + getTooltipItems: (List touchedSpots) { + return touchedSpots + .map((e) => LineTooltipItem(e.barIndex.toString(), textStyle1)) + .toList(); + }, + tooltipBorder: const BorderSide(color: Color(0x11111111), width: 2), + ); + final data = LineChartData( + minY: 0, + maxY: 10, + minX: 0, + maxX: 10, + titlesData: const FlTitlesData(show: false), + lineTouchData: LineTouchData( + touchTooltipData: tooltipData, + ), + ); + + final lineChartPainter = LineChartPainter(); + final holder = + PaintHolder(data, data, TextScaler.noScaling); + final mockCanvasWrapper = MockCanvasWrapper(); + when(mockCanvasWrapper.size).thenAnswer((realInvocation) => viewSize); + when(mockCanvasWrapper.canvas).thenReturn(MockCanvas()); + + final mockBuildContext = MockBuildContext(); + final mockUtils = MockUtils(); + Utils.changeInstance(mockUtils); + when(mockUtils.getThemeAwareTextStyle(any, any)) + .thenAnswer((realInvocation) => textStyle1); + when(mockUtils.calculateRotationOffset(any, any)) + .thenAnswer((realInvocation) => Offset.zero); + when( + mockCanvasWrapper.drawRotated( + size: anyNamed('size'), + rotationOffset: anyNamed('rotationOffset'), + drawOffset: anyNamed('drawOffset'), + angle: anyNamed('angle'), + drawCallback: anyNamed('drawCallback'), + ), + ).thenAnswer((realInvocation) { + final callback = realInvocation + .namedArguments[const Symbol('drawCallback')] as DrawCallback; + callback(); + }); + lineChartPainter.drawTouchTooltip( + mockBuildContext, + mockCanvasWrapper, + tooltipData, + barData.spots.first, + ShowingTooltipIndicators([ + LineBarSpot( + barData, + 0, + barData.spots.first, + ), + ]), + holder, + ); + + final result1 = + verify(mockCanvasWrapper.drawRRect(captureAny, captureAny)) + ..called(2); + final rRect = result1.captured[0] as RRect; + final paint = result1.captured[1] as Paint; + expect( + rRect, + RRect.fromLTRBR(22, 40, 60, 78, const Radius.circular(12)), + ); + expect(paint.color, const Color(0x11111111)); + final rRectBorder = result1.captured[2] as RRect; + final paintBorder = result1.captured[3] as Paint; + expect( + rRectBorder, + RRect.fromLTRBR(22, 40, 60, 78, const Radius.circular(12)), + ); + expect(paintBorder.color, const Color(0x11111111)); + expect(paintBorder.strokeWidth, 2); + + final result2 = verify(mockCanvasWrapper.drawText(captureAny, captureAny)) + ..called(1); + final textPainter = result2.captured[0] as TextPainter; + final drawOffset = result2.captured[1] as Offset; + expect((textPainter.text as TextSpan?)!.text, '0'); + expect((textPainter.text as TextSpan?)!.style, textStyle1); + expect(drawOffset, const Offset(34, 52)); + }); + + test('test 5 - should move tooltip 12 pixels to the left', () { + const viewSize = Size(100, 100); + + final barData = LineChartBarData( + spots: const [ + FlSpot(1, 1), + FlSpot(2, 2), + FlSpot(3, 3), + FlSpot(4, 4), + FlSpot.nullSpot, + FlSpot(5, 5), + ], + ); + + final tooltipData = LineTouchTooltipData( + tooltipBgColor: const Color(0x11111111), + tooltipRoundedRadius: 12, + rotateAngle: 43, + maxContentWidth: 100, + tooltipVerticalOffset: 12, + tooltipHorizontalAlignment: FLHorizontalAlignment.right, + tooltipPadding: const EdgeInsets.all(12), + tooltipMargin: const EdgeInsets.only(right: 12), + fitInsideVertically: true, + getTooltipItems: (List touchedSpots) { + return touchedSpots + .map((e) => LineTooltipItem(e.barIndex.toString(), textStyle1)) + .toList(); + }, + tooltipBorder: const BorderSide(color: Color(0x11111111), width: 2), + ); + final data = LineChartData( + minY: 0, + maxY: 10, + minX: 0, + maxX: 10, + titlesData: const FlTitlesData(show: false), + lineTouchData: LineTouchData( + touchTooltipData: tooltipData, + ), + ); + + final lineChartPainter = LineChartPainter(); + final holder = + PaintHolder(data, data, TextScaler.noScaling); + final mockCanvasWrapper = MockCanvasWrapper(); + when(mockCanvasWrapper.size).thenAnswer((realInvocation) => viewSize); + when(mockCanvasWrapper.canvas).thenReturn(MockCanvas()); + + final mockBuildContext = MockBuildContext(); + final mockUtils = MockUtils(); + Utils.changeInstance(mockUtils); + when(mockUtils.getThemeAwareTextStyle(any, any)) + .thenAnswer((realInvocation) => textStyle1); + when(mockUtils.calculateRotationOffset(any, any)) + .thenAnswer((realInvocation) => Offset.zero); + when( + mockCanvasWrapper.drawRotated( + size: anyNamed('size'), + rotationOffset: anyNamed('rotationOffset'), + drawOffset: anyNamed('drawOffset'), + angle: anyNamed('angle'), + drawCallback: anyNamed('drawCallback'), + ), + ).thenAnswer((realInvocation) { + final callback = realInvocation + .namedArguments[const Symbol('drawCallback')] as DrawCallback; + callback(); + }); + lineChartPainter.drawTouchTooltip( + mockBuildContext, + mockCanvasWrapper, + tooltipData, + barData.spots.first, + ShowingTooltipIndicators([ + LineBarSpot( + barData, + 0, + barData.spots.first, + ), + ]), + holder, + ); + + final result1 = + verify(mockCanvasWrapper.drawRRect(captureAny, captureAny)) + ..called(2); + final rRect = result1.captured[0] as RRect; + final paint = result1.captured[1] as Paint; + expect( + rRect, + RRect.fromLTRBR(-2, 40, 36, 78, const Radius.circular(12)), + ); + expect(paint.color, const Color(0x11111111)); + final rRectBorder = result1.captured[2] as RRect; + final paintBorder = result1.captured[3] as Paint; + expect( + rRectBorder, + RRect.fromLTRBR(-2, 40, 36, 78, const Radius.circular(12)), + ); + expect(paintBorder.color, const Color(0x11111111)); + expect(paintBorder.strokeWidth, 2); + + final result2 = verify(mockCanvasWrapper.drawText(captureAny, captureAny)) + ..called(1); + final textPainter = result2.captured[0] as TextPainter; + final drawOffset = result2.captured[1] as Offset; + expect((textPainter.text as TextSpan?)!.text, '0'); + expect((textPainter.text as TextSpan?)!.style, textStyle1); + expect(drawOffset, const Offset(10, 52)); + }); }); group('getBarLineXLength()', () { diff --git a/test/extensions/rect_extension_test.dart b/test/extensions/rect_extension_test.dart index 62da6afbf..68a83d7c1 100644 --- a/test/extensions/rect_extension_test.dart +++ b/test/extensions/rect_extension_test.dart @@ -34,19 +34,18 @@ void main() { const rect = Rect.fromLTWH(1, 1, 1, 1); const margin = EdgeInsets.zero; - expect(rect.applyMargin(margin), rect); + expect(rect.applyMargin(margin).center, Offset.zero); }); test('should move rect the correct amount', () { const rect = Rect.fromLTRB(25, 250, 100, 300); const margin = EdgeInsets.symmetric(vertical: 16, horizontal: 8); expect( - rect.applyMargin(margin), - Rect.fromLTRB( - 25 + margin.horizontal, - 250 - margin.vertical, - 100 + margin.horizontal, - 300 - margin.vertical, + rect.applyMargin(margin).center, + Offset( + // How to calculate symmetric? + rect.center.dx - 8 + 8, + rect.center.dy - 8 + 8, ), ); }); From e60f55b73c3423af4bb8a4998abfcb8479d28442 Mon Sep 17 00:00:00 2001 From: Jani Koponen Date: Sat, 17 Feb 2024 20:47:42 +0200 Subject: [PATCH 20/27] Modify padding/margin for LineLabels --- CHANGELOG.md | 12 +- .../samples/line/line_chart_sample8.dart | 4 +- lib/src/chart/bar_chart/bar_chart_data.dart | 2 +- .../base/axis_chart/axis_chart_data.dart | 16 ++- .../base/axis_chart/axis_chart_painter.dart | 110 ++++++++++++++---- lib/src/chart/line_chart/line_chart_data.dart | 9 +- .../scatter_chart/scatter_chart_data.dart | 2 +- lib/src/extensions/offset_extension.dart | 10 ++ lib/src/extensions/rect_extension.dart | 6 +- test/extensions/rect_extension_test.dart | 47 +++++++- 10 files changed, 171 insertions(+), 47 deletions(-) create mode 100644 lib/src/extensions/offset_extension.dart diff --git a/CHANGELOG.md b/CHANGELOG.md index a61e3f6dc..40524bcbc 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,6 +1,8 @@ ## newVersion -* **IMPROVEMENT** (by @k0psutin) Add `tooltipPadding` to BarTouchTooltipData, LineTouchTooltipData and ScatterTouchTooltipData, #824 +* **IMPROVEMENT** (by @k0psutin) Add `tooltipPadding` to BarTouchTooltipData, LineTouchTooltipData and ScatterTouchTooltipData, #824 +* **IMPROVEMENT** (by @k0psutin) Add `margin` to HorizontalLineLabel and VerticalLineLabel, #824 +* **BUGFIX** (by @k0psutin) Fix `padding` to apply padding correctly in HorizontalLineLabel and VerticalLineLabel, #824 * **BREAKING** (by @k0psutin) Update `tooltipMargin` to accept EdgeInsets, #824 * **BREAKING** (by @kopsutin) Add property `tooltipVerticalOffset` to BarTouchTooltipData, LineTouchTooltipData and ScatterTooltipItem to replace `tooltipMargin`, #824 ```dart @@ -12,7 +14,9 @@ BarTouchTooltipData( /// New way: BarTouchTooltipData( - tooltipVerticalOffset: -10, + tooltipVerticalOffset: -10, // same effect as old tooltipMargin + tooltipMargin: const EdgeInsets.only(left: 10), // New margin property that accepts EdgeInsets. Recommend to use EdgeInsets.only + tooltipPadding: const EdgeInsets.symmetric(horizontal: 16, vertical: 8), // Adds padding to tooltip ) ``` * **BREAKING** (by @k0psutin) Remove `tooltipMargin` property from ScatterTooltipItem, #824 @@ -25,7 +29,9 @@ ScatterTooltipItem( /// New way: ScatterTouchTooltipData( - tooltipVerticalOffset: 10, + tooltipVerticalOffset: 10, // same effect as old tooltipMargin + tooltipMargin: const EdgeInsets.only(left: 10), // New margin property that accepts EdgeInsets. Recommend to use EdgeInsets.only + tooltipPadding: const EdgeInsets.symmetric(horizontal: 16, vertical: 8), // Adds padding to tooltip ) ``` diff --git a/example/lib/presentation/samples/line/line_chart_sample8.dart b/example/lib/presentation/samples/line/line_chart_sample8.dart index 75b629a1c..d5a4f1ad4 100644 --- a/example/lib/presentation/samples/line/line_chart_sample8.dart +++ b/example/lib/presentation/samples/line/line_chart_sample8.dart @@ -150,7 +150,7 @@ class _LineChartSample8State extends State { label: HorizontalLineLabel( show: true, alignment: Alignment.topRight, - padding: const EdgeInsets.only(right: 5, bottom: 5), + margin: const EdgeInsets.only(right: 5, bottom: 5), style: const TextStyle( fontSize: 9, fontWeight: FontWeight.bold, @@ -168,7 +168,7 @@ class _LineChartSample8State extends State { label: VerticalLineLabel( show: true, alignment: Alignment.topRight, - padding: const EdgeInsets.only(left: 10, top: 5), + margin: const EdgeInsets.only(left: 10, top: 5), style: const TextStyle( fontSize: 9, fontWeight: FontWeight.bold, diff --git a/lib/src/chart/bar_chart/bar_chart_data.dart b/lib/src/chart/bar_chart/bar_chart_data.dart index 1aab10179..d199d8661 100644 --- a/lib/src/chart/bar_chart/bar_chart_data.dart +++ b/lib/src/chart/bar_chart/bar_chart_data.dart @@ -690,7 +690,7 @@ class BarTouchTooltipData with EquatableMixin { /// Tooltip shows on top of rods, with [tooltipBgColor] as a background color, /// and you can set corner radius using [tooltipRoundedRadius]. /// If you want to have tooltip padding, fill [tooltipPadding], - /// If you want to have tooltip margin, fill [tooltipMargin]. + /// If you want to have tooltip margin, fill [tooltipMargin]. Use EdgeInsets.only. Currently symmetric values cancels eachother out. /// If you want to adjust tooltip vertical position, set [tooltipVerticalOffset] /// If you want to adjust tooltip horizontal position, set [tooltipHorizontalOffset] /// Content of the tooltip will provide using [getTooltipItem] callback, you can override it diff --git a/lib/src/chart/base/axis_chart/axis_chart_data.dart b/lib/src/chart/base/axis_chart/axis_chart_data.dart index a5cddae35..ab6104f70 100644 --- a/lib/src/chart/base/axis_chart/axis_chart_data.dart +++ b/lib/src/chart/base/axis_chart/axis_chart_data.dart @@ -1116,13 +1116,14 @@ class VerticalLine extends FlLine with EquatableMixin { /// Draws a title on the [HorizontalLine] class HorizontalLineLabel extends FlLineLabel with EquatableMixin { /// Draws a title on the [HorizontalLine], align it with [alignment] over the line, - /// applies [padding] for spaces, and applies [style for changing color, + /// applies [padding] for label padding, applies [margin] for label space andapplies [style] for changing color, /// size, ... of the text. /// Drawing text will retrieve through [labelResolver], /// you can override it with your custom data. /// /// [show] determines showing label or not. HorizontalLineLabel({ EdgeInsets? padding, + EdgeInsets? margin, super.style, Alignment? alignment, super.show = false, @@ -1130,7 +1131,8 @@ class HorizontalLineLabel extends FlLineLabel with EquatableMixin { }) : labelResolver = labelResolver ?? HorizontalLineLabel.defaultLineLabelResolver, super( - padding: padding ?? const EdgeInsets.all(6), + padding: padding ?? EdgeInsets.zero, + margin: margin ?? EdgeInsets.zero, alignment: alignment ?? Alignment.topLeft, ); @@ -1163,6 +1165,7 @@ class HorizontalLineLabel extends FlLineLabel with EquatableMixin { labelResolver, show, padding, + margin, style, alignment, ]; @@ -1171,13 +1174,14 @@ class HorizontalLineLabel extends FlLineLabel with EquatableMixin { /// Draws a title on the [VerticalLine] class VerticalLineLabel extends FlLineLabel with EquatableMixin { /// Draws a title on the [VerticalLine], align it with [alignment] over the line, - /// applies [padding] for spaces, and applies [style for changing color, + /// applies [padding] for label padding, applies [margin] for label space andapplies [style] for changing color, /// size, ... of the text. /// Drawing text will retrieve through [labelResolver], /// you can override it with your custom data. /// [show] determines showing label or not. VerticalLineLabel({ EdgeInsets? padding, + EdgeInsets? margin, TextStyle? style, Alignment? alignment, bool? show, @@ -1186,7 +1190,8 @@ class VerticalLineLabel extends FlLineLabel with EquatableMixin { labelResolver ?? VerticalLineLabel.defaultLineLabelResolver, super( show: show ?? false, - padding: padding ?? const EdgeInsets.all(6), + padding: padding ?? EdgeInsets.zero, + margin: margin ?? EdgeInsets.zero, style: style ?? const TextStyle( color: Colors.black, @@ -1212,6 +1217,8 @@ class VerticalLineLabel extends FlLineLabel with EquatableMixin { return VerticalLineLabel( padding: EdgeInsets.lerp(a.padding as EdgeInsets, b.padding as EdgeInsets, t), + margin: + EdgeInsets.lerp(a.margin as EdgeInsets, b.margin as EdgeInsets, t), style: TextStyle.lerp(a.style, b.style, t), alignment: Alignment.lerp(a.alignment, b.alignment, t), labelResolver: b.labelResolver, @@ -1225,6 +1232,7 @@ class VerticalLineLabel extends FlLineLabel with EquatableMixin { labelResolver, show, padding, + margin, style, alignment, ]; diff --git a/lib/src/chart/base/axis_chart/axis_chart_painter.dart b/lib/src/chart/base/axis_chart/axis_chart_painter.dart index 4a2dc92c2..8720903fe 100644 --- a/lib/src/chart/base/axis_chart/axis_chart_painter.dart +++ b/lib/src/chart/base/axis_chart/axis_chart_painter.dart @@ -3,7 +3,9 @@ import 'package:fl_chart/src/chart/bar_chart/bar_chart_painter.dart'; import 'package:fl_chart/src/chart/base/axis_chart/axis_chart_helper.dart'; import 'package:fl_chart/src/chart/base/base_chart/base_chart_painter.dart'; import 'package:fl_chart/src/chart/line_chart/line_chart_painter.dart'; +import 'package:fl_chart/src/extensions/offset_extension.dart'; import 'package:fl_chart/src/extensions/paint_extension.dart'; +import 'package:fl_chart/src/extensions/rect_extension.dart'; import 'package:fl_chart/src/utils/canvas_wrapper.dart'; import 'package:fl_chart/src/utils/utils.dart'; import 'package:flutter/material.dart'; @@ -22,6 +24,8 @@ abstract class AxisChartPainter _rangeAnnotationPaint = Paint()..style = PaintingStyle.fill; + _labelBackgroundPaint = Paint()..style = PaintingStyle.fill; + _extraLinesPaint = Paint()..style = PaintingStyle.stroke; _imagePaint = Paint(); @@ -29,6 +33,7 @@ abstract class AxisChartPainter late Paint _gridPaint; late Paint _backgroundPaint; late Paint _extraLinesPaint; + late Paint _labelBackgroundPaint; late Paint _imagePaint; /// [_rangeAnnotationPaint] draws range annotations; @@ -292,29 +297,40 @@ abstract class AxisChartPainter final style = TextStyle(fontSize: 11, color: line.color).merge(label.style); final padding = label.padding as EdgeInsets; + final margin = label.margin as EdgeInsets; + final alignment = label.alignment; + + final backgroundColor = + Utils().getThemeAwareTextStyle(context, style).backgroundColor ?? + Colors.transparent; final span = TextSpan( text: label.labelResolver(line), - style: Utils().getThemeAwareTextStyle(context, style), + style: Utils().getThemeAwareTextStyle(context, style).copyWith( + backgroundColor: Colors.transparent, + ), ); final tp = TextPainter( text: span, textDirection: TextDirection.ltr, + )..layout(); + + final textArea = Rect.fromLTRB( + from.dx, + from.dy - tp.height, + to.dx - tp.width, + to.dy, ); - // ignore: cascade_invocations - tp.layout(); - canvasWrapper.drawText( + drawLineLabel( + backgroundColor, + alignment, + textArea, + margin, + padding, tp, - label.alignment.withinRect( - Rect.fromLTRB( - from.dx + padding.left, - from.dy - padding.bottom - tp.height, - to.dx - padding.right - tp.width, - to.dy + padding.top, - ), - ), + canvasWrapper, ); } } @@ -385,35 +401,81 @@ abstract class AxisChartPainter final style = TextStyle(fontSize: 11, color: line.color).merge(label.style); final padding = label.padding as EdgeInsets; + final margin = label.margin as EdgeInsets; + final alignment = label.alignment; + + final backgroundColor = + Utils().getThemeAwareTextStyle(context, style).backgroundColor ?? + Colors.transparent; final span = TextSpan( text: label.labelResolver(line), - style: Utils().getThemeAwareTextStyle(context, style), + style: Utils().getThemeAwareTextStyle(context, style).copyWith( + backgroundColor: Colors.transparent, + ), ); final tp = TextPainter( text: span, textDirection: TextDirection.ltr, + )..layout(); + + final textArea = Rect.fromLTRB( + to.dx - tp.width, + from.dy, + from.dx, + to.dy, ); - // ignore: cascade_invocations - tp.layout(); - canvasWrapper.drawText( + drawLineLabel( + backgroundColor, + alignment, + textArea, + margin, + padding, tp, - label.alignment.withinRect( - Rect.fromLTRB( - to.dx - padding.right - tp.width, - from.dy + padding.top, - from.dx + padding.left, - to.dy - padding.bottom, - ), - ), + canvasWrapper, ); } } } } + void drawLineLabel( + Color backgroundColor, + Alignment alignment, + Rect textArea, + EdgeInsets margin, + EdgeInsets padding, + TextPainter tp, + CanvasWrapper canvasWrapper, + ) { + final offset = alignment + .withinRect( + textArea, + ) + .applyEdgeInsets(margin); + + final backgroundRect = Rect.fromCenter( + center: Offset( + offset.dx + tp.width / 2, + offset.dy + tp.height / 2, + ), + width: tp.width, + height: tp.height, + ).applyPadding(padding); + + canvasWrapper + ..drawRect( + backgroundRect, + _labelBackgroundPaint..color = backgroundColor, + ) + ..drawText( + tp, + offset, + ); + } + /// With this function we can convert our [FlSpot] x /// to the view base axis x . /// the view 0, 0 is on the top/left, but the spots is bottom/left diff --git a/lib/src/chart/line_chart/line_chart_data.dart b/lib/src/chart/line_chart/line_chart_data.dart index 19222a8e7..b2cdd2e89 100644 --- a/lib/src/chart/line_chart/line_chart_data.dart +++ b/lib/src/chart/line_chart/line_chart_data.dart @@ -805,12 +805,13 @@ bool showAllDots(FlSpot spot, LineChartBarData barData) { /// Shows a text label abstract class FlLineLabel with EquatableMixin { /// Draws a title on the line, align it with [alignment] over the line, - /// applies [padding] for spaces, and applies [style] for changing color, + /// applies [padding] for label padding, applies [margin] for label space andapplies [style] for changing color, /// size, ... of the text. /// [show] determines showing label or not. const FlLineLabel({ required this.show, required this.padding, + required this.margin, required this.style, required this.alignment, }); @@ -821,6 +822,9 @@ abstract class FlLineLabel with EquatableMixin { /// Inner spaces around the drawing text. final EdgeInsetsGeometry padding; + /// Outer spaces around the drawing text. + final EdgeInsetsGeometry margin; + /// Sets style of the drawing text. final TextStyle? style; @@ -832,6 +836,7 @@ abstract class FlLineLabel with EquatableMixin { List get props => [ show, padding, + margin, style, alignment, ]; @@ -1025,7 +1030,7 @@ class LineTouchTooltipData with EquatableMixin { /// Tooltip shows on top of spots, with [tooltipBgColor] as a background color, /// and you can set corner radius using [tooltipRoundedRadius]. /// If you want to have tooltip padding, fill [tooltipPadding], - /// If you want to have tooltip margin, fill [tooltipMargin]. + /// If you want to have tooltip margin, fill [tooltipMargin]. Use EdgeInsets.only. Currently symmetric values cancels eachother out. /// If you want to adjust tooltip vertical position, set [tooltipVerticalOffset] /// If you want to adjust tooltip horizontal position, set [tooltipHorizontalOffset] /// Content of the tooltip will provide using [getTooltipItems] callback, you can override it diff --git a/lib/src/chart/scatter_chart/scatter_chart_data.dart b/lib/src/chart/scatter_chart/scatter_chart_data.dart index 9b8e20033..136170d83 100644 --- a/lib/src/chart/scatter_chart/scatter_chart_data.dart +++ b/lib/src/chart/scatter_chart/scatter_chart_data.dart @@ -393,7 +393,7 @@ class ScatterTouchTooltipData with EquatableMixin { /// Tooltip shows on top of spots, with [tooltipBgColor] as a background color, /// and you can set corner radius using [tooltipRoundedRadius]. /// If you want to have tooltip padding, fill [tooltipPadding], - /// If you want to have tooltip margin, fill [tooltipMargin]. + /// If you want to have tooltip margin, fill [tooltipMargin]. Use EdgeInsets.only. Currently symmetric values cancels eachother out. /// If you want to adjust tooltip vertical position, set [tooltipVerticalOffset] /// If you want to adjust tooltip horizontal position, set [tooltipHorizontalOffset] /// Content of the tooltip will provide using [getTooltipItems] callback, you can override it diff --git a/lib/src/extensions/offset_extension.dart b/lib/src/extensions/offset_extension.dart new file mode 100644 index 000000000..2e2d80c8d --- /dev/null +++ b/lib/src/extensions/offset_extension.dart @@ -0,0 +1,10 @@ +import 'package:flutter/widgets.dart'; + +extension OffsetExtension on Offset { + Offset applyEdgeInsets(EdgeInsets inset) { + return Offset( + dx - inset.right + inset.left, + dy - inset.bottom + inset.top, + ); + } +} diff --git a/lib/src/extensions/rect_extension.dart b/lib/src/extensions/rect_extension.dart index 3df2f4876..797098da2 100644 --- a/lib/src/extensions/rect_extension.dart +++ b/lib/src/extensions/rect_extension.dart @@ -1,3 +1,4 @@ +import 'package:fl_chart/src/extensions/offset_extension.dart'; import 'package:flutter/material.dart'; extension RectExtension on Rect { @@ -11,10 +12,7 @@ extension RectExtension on Rect { } Rect applyMargin(EdgeInsets margin) => Rect.fromCenter( - center: Offset( - center.dx - margin.right + margin.left, - center.dy - margin.bottom + margin.top, - ), + center: center.applyEdgeInsets(margin), width: width, height: height, ); diff --git a/test/extensions/rect_extension_test.dart b/test/extensions/rect_extension_test.dart index 68a83d7c1..58a3b5313 100644 --- a/test/extensions/rect_extension_test.dart +++ b/test/extensions/rect_extension_test.dart @@ -34,18 +34,53 @@ void main() { const rect = Rect.fromLTWH(1, 1, 1, 1); const margin = EdgeInsets.zero; - expect(rect.applyMargin(margin).center, Offset.zero); + expect(rect.applyMargin(margin).center, rect.center); }); - test('should move rect the correct amount', () { + test('should move rect the correct amount with right padding', () { const rect = Rect.fromLTRB(25, 250, 100, 300); - const margin = EdgeInsets.symmetric(vertical: 16, horizontal: 8); + const margin = EdgeInsets.only(right: 10); expect( rect.applyMargin(margin).center, Offset( - // How to calculate symmetric? - rect.center.dx - 8 + 8, - rect.center.dy - 8 + 8, + rect.center.dx - 10, + rect.center.dy, + ), + ); + }); + + test('should move rect the correct amount with left padding', () { + const rect = Rect.fromLTRB(25, 250, 100, 300); + const margin = EdgeInsets.only(left: 10); + expect( + rect.applyMargin(margin).center, + Offset( + rect.center.dx + 10, + rect.center.dy, + ), + ); + }); + + test('should move rect the correct amount with bottom padding', () { + const rect = Rect.fromLTRB(25, 250, 100, 300); + const margin = EdgeInsets.only(bottom: 10); + expect( + rect.applyMargin(margin).center, + Offset( + rect.center.dx, + rect.center.dy - 10, + ), + ); + }); + + test('should move rect the correct amount with top padding', () { + const rect = Rect.fromLTRB(25, 250, 100, 300); + const margin = EdgeInsets.only(top: 10); + expect( + rect.applyMargin(margin).center, + Offset( + rect.center.dx, + rect.center.dy + 10, ), ); }); From 813e9587e0500e31f0937c734456e3d6d886e7ce Mon Sep 17 00:00:00 2001 From: Jani Koponen Date: Sat, 2 Mar 2024 12:48:09 +0200 Subject: [PATCH 21/27] Remove margin and tooltipMargin --- CHANGELOG.md | 11 ++-- .../samples/line/line_chart_sample8.dart | 6 +- example/windows/runner/flutter_window.cpp | 5 ++ lib/src/chart/bar_chart/bar_chart_data.dart | 7 --- .../chart/bar_chart/bar_chart_painter.dart | 4 +- .../base/axis_chart/axis_chart_data.dart | 26 ++++++--- .../base/axis_chart/axis_chart_painter.dart | 34 ++++++----- lib/src/chart/line_chart/line_chart_data.dart | 17 +++--- .../chart/line_chart/line_chart_painter.dart | 4 +- .../scatter_chart/scatter_chart_data.dart | 9 --- .../scatter_chart/scatter_chart_painter.dart | 4 +- lib/src/extensions/offset_extension.dart | 10 ---- lib/src/extensions/rect_extension.dart | 7 --- repo_files/documentations/bar_chart.md | 2 +- repo_files/documentations/line_chart.md | 2 +- .../line_chart/line_chart_painter_test.dart | 4 +- test/extensions/rect_extension_test.dart | 57 ------------------- 17 files changed, 66 insertions(+), 143 deletions(-) delete mode 100644 lib/src/extensions/offset_extension.dart diff --git a/CHANGELOG.md b/CHANGELOG.md index 40524bcbc..be9da14f6 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,10 +1,13 @@ ## newVersion * **IMPROVEMENT** (by @k0psutin) Add `tooltipPadding` to BarTouchTooltipData, LineTouchTooltipData and ScatterTouchTooltipData, #824 -* **IMPROVEMENT** (by @k0psutin) Add `margin` to HorizontalLineLabel and VerticalLineLabel, #824 -* **BUGFIX** (by @k0psutin) Fix `padding` to apply padding correctly in HorizontalLineLabel and VerticalLineLabel, #824 -* **BREAKING** (by @k0psutin) Update `tooltipMargin` to accept EdgeInsets, #824 +* **BREAKING** (by @k0psutin) Remove `margin` from HorizontalLineLabel and VerticalLineLabel, #824 +* **IMPROVEMENT** (by @k0psutin) Add `verticalOFfset` and `horizontalOffset` to HorizontalLineLabel and VerticalLineLabel to replace `margin`, #824 +* **BREAKING** (by @k0psutin) Remove `tooltipMargin` from HorizontalLineLabel and VerticalLineLabel, #824 * **BREAKING** (by @kopsutin) Add property `tooltipVerticalOffset` to BarTouchTooltipData, LineTouchTooltipData and ScatterTooltipItem to replace `tooltipMargin`, #824 +* **BUGFIX** (by @k0psutin) Fix `padding` to apply padding correctly in HorizontalLineLabel and VerticalLineLabel, #824 + + ```dart /// Migration guide: /// Old way: @@ -15,7 +18,6 @@ BarTouchTooltipData( /// New way: BarTouchTooltipData( tooltipVerticalOffset: -10, // same effect as old tooltipMargin - tooltipMargin: const EdgeInsets.only(left: 10), // New margin property that accepts EdgeInsets. Recommend to use EdgeInsets.only tooltipPadding: const EdgeInsets.symmetric(horizontal: 16, vertical: 8), // Adds padding to tooltip ) ``` @@ -30,7 +32,6 @@ ScatterTooltipItem( /// New way: ScatterTouchTooltipData( tooltipVerticalOffset: 10, // same effect as old tooltipMargin - tooltipMargin: const EdgeInsets.only(left: 10), // New margin property that accepts EdgeInsets. Recommend to use EdgeInsets.only tooltipPadding: const EdgeInsets.symmetric(horizontal: 16, vertical: 8), // Adds padding to tooltip ) ``` diff --git a/example/lib/presentation/samples/line/line_chart_sample8.dart b/example/lib/presentation/samples/line/line_chart_sample8.dart index d5a4f1ad4..cff91ffc6 100644 --- a/example/lib/presentation/samples/line/line_chart_sample8.dart +++ b/example/lib/presentation/samples/line/line_chart_sample8.dart @@ -150,7 +150,8 @@ class _LineChartSample8State extends State { label: HorizontalLineLabel( show: true, alignment: Alignment.topRight, - margin: const EdgeInsets.only(right: 5, bottom: 5), + verticalOffset: 5.0, + horizontalOffset: -5.0, style: const TextStyle( fontSize: 9, fontWeight: FontWeight.bold, @@ -168,7 +169,8 @@ class _LineChartSample8State extends State { label: VerticalLineLabel( show: true, alignment: Alignment.topRight, - margin: const EdgeInsets.only(left: 10, top: 5), + verticalOffset: -5.0, + horizontalOffset: 10, style: const TextStyle( fontSize: 9, fontWeight: FontWeight.bold, diff --git a/example/windows/runner/flutter_window.cpp b/example/windows/runner/flutter_window.cpp index 490813deb..c819cb083 100644 --- a/example/windows/runner/flutter_window.cpp +++ b/example/windows/runner/flutter_window.cpp @@ -31,6 +31,11 @@ bool FlutterWindow::OnCreate() { this->Show(); }); + // Flutter can complete the first frame before the "show window" callback is + // registered. The following call ensures a frame is pending to ensure the + // window is shown. It is a no-op if the first frame hasn't completed yet. + flutter_controller_->ForceRedraw(); + return true; } diff --git a/lib/src/chart/bar_chart/bar_chart_data.dart b/lib/src/chart/bar_chart/bar_chart_data.dart index d199d8661..43325a244 100644 --- a/lib/src/chart/bar_chart/bar_chart_data.dart +++ b/lib/src/chart/bar_chart/bar_chart_data.dart @@ -690,7 +690,6 @@ class BarTouchTooltipData with EquatableMixin { /// Tooltip shows on top of rods, with [tooltipBgColor] as a background color, /// and you can set corner radius using [tooltipRoundedRadius]. /// If you want to have tooltip padding, fill [tooltipPadding], - /// If you want to have tooltip margin, fill [tooltipMargin]. Use EdgeInsets.only. Currently symmetric values cancels eachother out. /// If you want to adjust tooltip vertical position, set [tooltipVerticalOffset] /// If you want to adjust tooltip horizontal position, set [tooltipHorizontalOffset] /// Content of the tooltip will provide using [getTooltipItem] callback, you can override it @@ -703,7 +702,6 @@ class BarTouchTooltipData with EquatableMixin { Color? tooltipBgColor, double? tooltipRoundedRadius, EdgeInsets? tooltipPadding, - EdgeInsets? tooltipMargin, FLHorizontalAlignment? tooltipHorizontalAlignment, double? tooltipVerticalOffset, double? tooltipHorizontalOffset, @@ -718,7 +716,6 @@ class BarTouchTooltipData with EquatableMixin { tooltipRoundedRadius = tooltipRoundedRadius ?? 4, tooltipPadding = tooltipPadding ?? const EdgeInsets.symmetric(horizontal: 16, vertical: 8), - tooltipMargin = tooltipMargin ?? EdgeInsets.zero, tooltipVerticalOffset = tooltipVerticalOffset ?? 16, tooltipHorizontalAlignment = tooltipHorizontalAlignment ?? FLHorizontalAlignment.center, @@ -741,9 +738,6 @@ class BarTouchTooltipData with EquatableMixin { /// Applies a padding for showing contents inside the tooltip. final EdgeInsets tooltipPadding; - /// Applies a margin for content - final EdgeInsets tooltipMargin; - /// Controls showing tooltip on left side, right side or center aligned with rod, default is center final FLHorizontalAlignment tooltipHorizontalAlignment; @@ -780,7 +774,6 @@ class BarTouchTooltipData with EquatableMixin { tooltipBgColor, tooltipRoundedRadius, tooltipPadding, - tooltipMargin, tooltipVerticalOffset, tooltipHorizontalAlignment, tooltipHorizontalOffset, diff --git a/lib/src/chart/bar_chart/bar_chart_painter.dart b/lib/src/chart/bar_chart/bar_chart_painter.dart index 3e59eaccf..4deafae9a 100644 --- a/lib/src/chart/bar_chart/bar_chart_painter.dart +++ b/lib/src/chart/bar_chart/bar_chart_painter.dart @@ -415,9 +415,7 @@ class BarChartPainter extends AxisChartPainter { tooltipTop, tooltipWidth, tooltipHeight, - ) - .applyPadding(tooltipData.tooltipPadding) - .applyMargin(tooltipData.tooltipMargin); + ).applyPadding(tooltipData.tooltipPadding); if (tooltipData.fitInsideHorizontally) { if (rect.left < 0) { diff --git a/lib/src/chart/base/axis_chart/axis_chart_data.dart b/lib/src/chart/base/axis_chart/axis_chart_data.dart index ab6104f70..483994c0a 100644 --- a/lib/src/chart/base/axis_chart/axis_chart_data.dart +++ b/lib/src/chart/base/axis_chart/axis_chart_data.dart @@ -1123,7 +1123,8 @@ class HorizontalLineLabel extends FlLineLabel with EquatableMixin { /// /// [show] determines showing label or not. HorizontalLineLabel({ EdgeInsets? padding, - EdgeInsets? margin, + double? horizontalOffset, + double? verticalOffset, super.style, Alignment? alignment, super.show = false, @@ -1132,7 +1133,8 @@ class HorizontalLineLabel extends FlLineLabel with EquatableMixin { labelResolver ?? HorizontalLineLabel.defaultLineLabelResolver, super( padding: padding ?? EdgeInsets.zero, - margin: margin ?? EdgeInsets.zero, + horizontalOffset: horizontalOffset ?? 0.0, + verticalOffset: verticalOffset ?? 0.0, alignment: alignment ?? Alignment.topLeft, ); @@ -1152,6 +1154,8 @@ class HorizontalLineLabel extends FlLineLabel with EquatableMixin { return HorizontalLineLabel( padding: EdgeInsets.lerp(a.padding as EdgeInsets, b.padding as EdgeInsets, t), + horizontalOffset: lerpDouble(a.horizontalOffset, b.horizontalOffset, t), + verticalOffset: lerpDouble(a.verticalOffset, b.verticalOffset, t), style: TextStyle.lerp(a.style, b.style, t), alignment: Alignment.lerp(a.alignment, b.alignment, t), labelResolver: b.labelResolver, @@ -1165,7 +1169,8 @@ class HorizontalLineLabel extends FlLineLabel with EquatableMixin { labelResolver, show, padding, - margin, + horizontalOffset, + verticalOffset, style, alignment, ]; @@ -1174,14 +1179,15 @@ class HorizontalLineLabel extends FlLineLabel with EquatableMixin { /// Draws a title on the [VerticalLine] class VerticalLineLabel extends FlLineLabel with EquatableMixin { /// Draws a title on the [VerticalLine], align it with [alignment] over the line, - /// applies [padding] for label padding, applies [margin] for label space andapplies [style] for changing color, + /// applies [padding] for label padding, [style] for changing color, /// size, ... of the text. /// Drawing text will retrieve through [labelResolver], /// you can override it with your custom data. /// [show] determines showing label or not. VerticalLineLabel({ EdgeInsets? padding, - EdgeInsets? margin, + double? horizontalOffset, + double? verticalOffset, TextStyle? style, Alignment? alignment, bool? show, @@ -1191,7 +1197,8 @@ class VerticalLineLabel extends FlLineLabel with EquatableMixin { super( show: show ?? false, padding: padding ?? EdgeInsets.zero, - margin: margin ?? EdgeInsets.zero, + horizontalOffset: horizontalOffset ?? 0.0, + verticalOffset: verticalOffset ?? 0.0, style: style ?? const TextStyle( color: Colors.black, @@ -1217,8 +1224,8 @@ class VerticalLineLabel extends FlLineLabel with EquatableMixin { return VerticalLineLabel( padding: EdgeInsets.lerp(a.padding as EdgeInsets, b.padding as EdgeInsets, t), - margin: - EdgeInsets.lerp(a.margin as EdgeInsets, b.margin as EdgeInsets, t), + horizontalOffset: lerpDouble(a.horizontalOffset, b.horizontalOffset, t), + verticalOffset: lerpDouble(a.verticalOffset, b.verticalOffset, t), style: TextStyle.lerp(a.style, b.style, t), alignment: Alignment.lerp(a.alignment, b.alignment, t), labelResolver: b.labelResolver, @@ -1232,7 +1239,8 @@ class VerticalLineLabel extends FlLineLabel with EquatableMixin { labelResolver, show, padding, - margin, + horizontalOffset, + verticalOffset, style, alignment, ]; diff --git a/lib/src/chart/base/axis_chart/axis_chart_painter.dart b/lib/src/chart/base/axis_chart/axis_chart_painter.dart index 8720903fe..64507ed4f 100644 --- a/lib/src/chart/base/axis_chart/axis_chart_painter.dart +++ b/lib/src/chart/base/axis_chart/axis_chart_painter.dart @@ -3,7 +3,6 @@ import 'package:fl_chart/src/chart/bar_chart/bar_chart_painter.dart'; import 'package:fl_chart/src/chart/base/axis_chart/axis_chart_helper.dart'; import 'package:fl_chart/src/chart/base/base_chart/base_chart_painter.dart'; import 'package:fl_chart/src/chart/line_chart/line_chart_painter.dart'; -import 'package:fl_chart/src/extensions/offset_extension.dart'; import 'package:fl_chart/src/extensions/paint_extension.dart'; import 'package:fl_chart/src/extensions/rect_extension.dart'; import 'package:fl_chart/src/utils/canvas_wrapper.dart'; @@ -297,7 +296,8 @@ abstract class AxisChartPainter final style = TextStyle(fontSize: 11, color: line.color).merge(label.style); final padding = label.padding as EdgeInsets; - final margin = label.margin as EdgeInsets; + final verticalOffset = label.verticalOffset; + final horizontalOffset = label.horizontalOffset; final alignment = label.alignment; final backgroundColor = @@ -327,8 +327,9 @@ abstract class AxisChartPainter backgroundColor, alignment, textArea, - margin, padding, + verticalOffset, + horizontalOffset, tp, canvasWrapper, ); @@ -401,7 +402,8 @@ abstract class AxisChartPainter final style = TextStyle(fontSize: 11, color: line.color).merge(label.style); final padding = label.padding as EdgeInsets; - final margin = label.margin as EdgeInsets; + final verticalOffset = label.verticalOffset; + final horizontalOffset = label.horizontalOffset; final alignment = label.alignment; final backgroundColor = @@ -431,8 +433,9 @@ abstract class AxisChartPainter backgroundColor, alignment, textArea, - margin, padding, + verticalOffset, + horizontalOffset, tp, canvasWrapper, ); @@ -445,21 +448,25 @@ abstract class AxisChartPainter Color backgroundColor, Alignment alignment, Rect textArea, - EdgeInsets margin, EdgeInsets padding, + double verticalOffset, + double horizontalOffset, TextPainter tp, CanvasWrapper canvasWrapper, ) { - final offset = alignment - .withinRect( - textArea, - ) - .applyEdgeInsets(margin); + final currenfOffset = alignment.withinRect( + textArea, + ); + + final offset = Offset( + currenfOffset.dx + horizontalOffset, + currenfOffset.dy - verticalOffset, + ); final backgroundRect = Rect.fromCenter( center: Offset( - offset.dx + tp.width / 2, - offset.dy + tp.height / 2, + offset.dx + (tp.width / 2), + offset.dy + (tp.height / 2), ), width: tp.width, height: tp.height, @@ -501,7 +508,6 @@ abstract class AxisChartPainter /// With this function we can get horizontal /// position for the tooltip. - /// double getTooltipLeft( double dx, double tooltipWidth, diff --git a/lib/src/chart/line_chart/line_chart_data.dart b/lib/src/chart/line_chart/line_chart_data.dart index b2cdd2e89..6d03184e6 100644 --- a/lib/src/chart/line_chart/line_chart_data.dart +++ b/lib/src/chart/line_chart/line_chart_data.dart @@ -811,7 +811,8 @@ abstract class FlLineLabel with EquatableMixin { const FlLineLabel({ required this.show, required this.padding, - required this.margin, + required this.horizontalOffset, + required this.verticalOffset, required this.style, required this.alignment, }); @@ -822,8 +823,9 @@ abstract class FlLineLabel with EquatableMixin { /// Inner spaces around the drawing text. final EdgeInsetsGeometry padding; - /// Outer spaces around the drawing text. - final EdgeInsetsGeometry margin; + final double verticalOffset; + + final double horizontalOffset; /// Sets style of the drawing text. final TextStyle? style; @@ -836,7 +838,8 @@ abstract class FlLineLabel with EquatableMixin { List get props => [ show, padding, - margin, + verticalOffset, + horizontalOffset, style, alignment, ]; @@ -1030,7 +1033,6 @@ class LineTouchTooltipData with EquatableMixin { /// Tooltip shows on top of spots, with [tooltipBgColor] as a background color, /// and you can set corner radius using [tooltipRoundedRadius]. /// If you want to have tooltip padding, fill [tooltipPadding], - /// If you want to have tooltip margin, fill [tooltipMargin]. Use EdgeInsets.only. Currently symmetric values cancels eachother out. /// If you want to adjust tooltip vertical position, set [tooltipVerticalOffset] /// If you want to adjust tooltip horizontal position, set [tooltipHorizontalOffset] /// Content of the tooltip will provide using [getTooltipItems] callback, you can override it @@ -1044,7 +1046,6 @@ class LineTouchTooltipData with EquatableMixin { this.tooltipRoundedRadius = 4, this.tooltipPadding = const EdgeInsets.symmetric(horizontal: 16, vertical: 8), - this.tooltipMargin = EdgeInsets.zero, this.tooltipHorizontalAlignment = FLHorizontalAlignment.center, this.tooltipVerticalOffset = 16, this.tooltipHorizontalOffset = 0, @@ -1066,9 +1067,6 @@ class LineTouchTooltipData with EquatableMixin { /// Applies a padding for showing contents inside the tooltip. final EdgeInsets tooltipPadding; - /// Applies a margin for content - final EdgeInsets tooltipMargin; - /// Controls showing tooltip on left side, right side or center aligned with spot, default is center final FLHorizontalAlignment tooltipHorizontalAlignment; @@ -1105,7 +1103,6 @@ class LineTouchTooltipData with EquatableMixin { tooltipBgColor, tooltipRoundedRadius, tooltipPadding, - tooltipMargin, tooltipVerticalOffset, tooltipHorizontalAlignment, tooltipHorizontalOffset, diff --git a/lib/src/chart/line_chart/line_chart_painter.dart b/lib/src/chart/line_chart/line_chart_painter.dart index e9700a356..8bdbaa0a2 100644 --- a/lib/src/chart/line_chart/line_chart_painter.dart +++ b/lib/src/chart/line_chart/line_chart_painter.dart @@ -1078,9 +1078,7 @@ class LineChartPainter extends AxisChartPainter { tooltipTopPosition, tooltipWidth, tooltipHeight, - ) - .applyPadding(tooltipData.tooltipPadding) - .applyMargin(tooltipData.tooltipMargin); + ).applyPadding(tooltipData.tooltipPadding); if (tooltipData.fitInsideHorizontally) { if (rect.left < 0) { diff --git a/lib/src/chart/scatter_chart/scatter_chart_data.dart b/lib/src/chart/scatter_chart/scatter_chart_data.dart index 136170d83..355154ce3 100644 --- a/lib/src/chart/scatter_chart/scatter_chart_data.dart +++ b/lib/src/chart/scatter_chart/scatter_chart_data.dart @@ -393,7 +393,6 @@ class ScatterTouchTooltipData with EquatableMixin { /// Tooltip shows on top of spots, with [tooltipBgColor] as a background color, /// and you can set corner radius using [tooltipRoundedRadius]. /// If you want to have tooltip padding, fill [tooltipPadding], - /// If you want to have tooltip margin, fill [tooltipMargin]. Use EdgeInsets.only. Currently symmetric values cancels eachother out. /// If you want to adjust tooltip vertical position, set [tooltipVerticalOffset] /// If you want to adjust tooltip horizontal position, set [tooltipHorizontalOffset] /// Content of the tooltip will provide using [getTooltipItems] callback, you can override it @@ -406,7 +405,6 @@ class ScatterTouchTooltipData with EquatableMixin { Color? tooltipBgColor, double? tooltipRoundedRadius, EdgeInsets? tooltipPadding, - EdgeInsets? tooltipMargin, FLHorizontalAlignment? tooltipHorizontalAlignment, double? tooltipVerticalOffset, double? tooltipHorizontalOffset, @@ -420,7 +418,6 @@ class ScatterTouchTooltipData with EquatableMixin { tooltipRoundedRadius = tooltipRoundedRadius ?? 4, tooltipPadding = tooltipPadding ?? const EdgeInsets.symmetric(horizontal: 16, vertical: 8), - tooltipMargin = tooltipMargin ?? EdgeInsets.zero, tooltipHorizontalAlignment = tooltipHorizontalAlignment ?? FLHorizontalAlignment.center, tooltipHorizontalOffset = tooltipHorizontalOffset ?? 0, @@ -442,9 +439,6 @@ class ScatterTouchTooltipData with EquatableMixin { /// Applies a padding for showing contents inside the tooltip. final EdgeInsets tooltipPadding; - /// Applies a margin for content - final EdgeInsets tooltipMargin; - /// Controls showing tooltip on left side, right side or center aligned with spot, default is center final FLHorizontalAlignment tooltipHorizontalAlignment; @@ -477,7 +471,6 @@ class ScatterTouchTooltipData with EquatableMixin { List get props => [ tooltipBgColor, tooltipRoundedRadius, - tooltipMargin, tooltipPadding, tooltipHorizontalAlignment, tooltipHorizontalOffset, @@ -495,7 +488,6 @@ class ScatterTouchTooltipData with EquatableMixin { ScatterTouchTooltipData copyWith({ Color? tooltipBgColor, double? tooltipRoundedRadius, - EdgeInsets? tooltipMargin, EdgeInsets? tooltipPadding, FLHorizontalAlignment? tooltipHorizontalAlignment, double? tooltipVerticalOffset, @@ -510,7 +502,6 @@ class ScatterTouchTooltipData with EquatableMixin { return ScatterTouchTooltipData( tooltipBgColor: tooltipBgColor ?? this.tooltipBgColor, tooltipRoundedRadius: tooltipRoundedRadius ?? this.tooltipRoundedRadius, - tooltipMargin: tooltipMargin ?? this.tooltipMargin, tooltipPadding: tooltipPadding ?? this.tooltipPadding, tooltipHorizontalAlignment: tooltipHorizontalAlignment ?? this.tooltipHorizontalAlignment, diff --git a/lib/src/chart/scatter_chart/scatter_chart_painter.dart b/lib/src/chart/scatter_chart/scatter_chart_painter.dart index 21a769a46..68f6e3f12 100644 --- a/lib/src/chart/scatter_chart/scatter_chart_painter.dart +++ b/lib/src/chart/scatter_chart/scatter_chart_painter.dart @@ -260,9 +260,7 @@ class ScatterChartPainter extends AxisChartPainter { (tooltipData.tooltipPadding.vertical / 2), tooltipWidth, tooltipHeight, - ) - .applyPadding(tooltipData.tooltipPadding) - .applyMargin(tooltipData.tooltipMargin); + ).applyPadding(tooltipData.tooltipPadding); if (tooltipData.fitInsideHorizontally) { if (rect.left < 0) { diff --git a/lib/src/extensions/offset_extension.dart b/lib/src/extensions/offset_extension.dart deleted file mode 100644 index 2e2d80c8d..000000000 --- a/lib/src/extensions/offset_extension.dart +++ /dev/null @@ -1,10 +0,0 @@ -import 'package:flutter/widgets.dart'; - -extension OffsetExtension on Offset { - Offset applyEdgeInsets(EdgeInsets inset) { - return Offset( - dx - inset.right + inset.left, - dy - inset.bottom + inset.top, - ); - } -} diff --git a/lib/src/extensions/rect_extension.dart b/lib/src/extensions/rect_extension.dart index 797098da2..f366ceb56 100644 --- a/lib/src/extensions/rect_extension.dart +++ b/lib/src/extensions/rect_extension.dart @@ -1,4 +1,3 @@ -import 'package:fl_chart/src/extensions/offset_extension.dart'; import 'package:flutter/material.dart'; extension RectExtension on Rect { @@ -10,10 +9,4 @@ extension RectExtension on Rect { bottom + padding.bottom, ); } - - Rect applyMargin(EdgeInsets margin) => Rect.fromCenter( - center: center.applyEdgeInsets(margin), - width: width, - height: height, - ); } diff --git a/repo_files/documentations/bar_chart.md b/repo_files/documentations/bar_chart.md index 37478cf53..0a5fb343b 100644 --- a/repo_files/documentations/bar_chart.md +++ b/repo_files/documentations/bar_chart.md @@ -99,9 +99,9 @@ enum values {`start`, `end`, `center`, `spaceEvenly`, `spaceAround`, `spaceBetwe |tooltipBorder|border of the tooltip bubble|BorderSide.none| |tooltipRoundedRadius|background corner radius of the tooltip bubble|4| |tooltipPadding|padding of the tooltip|EdgeInsets.symmetric(horizontal: 16, vertical: 8)| - |tooltipMargin|margin between the tooltip and the touched spot|16| |tooltipHorizontalAlignment|horizontal alginment of tooltip relative to the bar|FLHorizontalAlignment.center| |tooltipHorizontalOffset|horizontal offset of tooltip|0| + |tooltipVerticalOffset|vertical offset of tooltip|0| |maxContentWidth|maximum width of the tooltip (if a text row is wider than this, then the text breaks to a new line|120| |getTooltipItems|a callback that retrieve [BarTooltipItem](#BarTooltipItem) by the given [BarChartGroupData](#BarChartGroupData), groupIndex, [BarChartRodData](#BarChartRodData) and rodIndex |defaultBarTooltipItem| |fitInsideHorizontally| forces tooltip to horizontally shift inside the chart's bounding box| false| diff --git a/repo_files/documentations/line_chart.md b/repo_files/documentations/line_chart.md index 00bc36973..4b6d4ef80 100644 --- a/repo_files/documentations/line_chart.md +++ b/repo_files/documentations/line_chart.md @@ -123,9 +123,9 @@ When you change the chart's state, it animates to the new state internally (usin |tooltipBorder|border of the tooltip bubble|BorderSide.none| |tooltipRoundedRadius|background corner radius of the tooltip bubble|4| |tooltipPadding|padding of the tooltip|EdgeInsets.symmetric(horizontal: 16, vertical: 8)| - |tooltipMargin|margin between the tooltip and the touched spot|16| |tooltipHorizontalAlignment|horizontal alginment of tooltip relative to the spot|FLHorizontalAlignment.center| |tooltipHorizontalOffset|horizontal offset of tooltip|0| + |tooltipVerticalOffset|Vertical offset of tooltip|16| |maxContentWidth|maximum width of the tooltip (if a text row is wider than this, then the text breaks to a new line|120| |getTooltipItems|a callback that retrieve list of [LineTooltipItem](#LineTooltipItem) by the given list of [LineBarSpot](#LineBarSpot) |defaultLineTooltipItem| |fitInsideHorizontally| forces tooltip to horizontally shift inside the chart's bounding box| false| diff --git a/test/chart/line_chart/line_chart_painter_test.dart b/test/chart/line_chart/line_chart_painter_test.dart index 2e8ef8731..cb156a553 100644 --- a/test/chart/line_chart/line_chart_painter_test.dart +++ b/test/chart/line_chart/line_chart_painter_test.dart @@ -2647,9 +2647,9 @@ void main() { rotateAngle: 43, maxContentWidth: 100, tooltipVerticalOffset: 12, + tooltipHorizontalOffset: 12, tooltipHorizontalAlignment: FLHorizontalAlignment.right, tooltipPadding: const EdgeInsets.all(12), - tooltipMargin: const EdgeInsets.only(left: 12), fitInsideVertically: true, getTooltipItems: (List touchedSpots) { return touchedSpots @@ -2759,9 +2759,9 @@ void main() { rotateAngle: 43, maxContentWidth: 100, tooltipVerticalOffset: 12, + tooltipHorizontalOffset: -12, tooltipHorizontalAlignment: FLHorizontalAlignment.right, tooltipPadding: const EdgeInsets.all(12), - tooltipMargin: const EdgeInsets.only(right: 12), fitInsideVertically: true, getTooltipItems: (List touchedSpots) { return touchedSpots diff --git a/test/extensions/rect_extension_test.dart b/test/extensions/rect_extension_test.dart index 58a3b5313..00693f4b7 100644 --- a/test/extensions/rect_extension_test.dart +++ b/test/extensions/rect_extension_test.dart @@ -28,62 +28,5 @@ void main() { ); }); }); - - group('addMargin', () { - test('should not affect with EdgeInsets.zero', () { - const rect = Rect.fromLTWH(1, 1, 1, 1); - const margin = EdgeInsets.zero; - - expect(rect.applyMargin(margin).center, rect.center); - }); - - test('should move rect the correct amount with right padding', () { - const rect = Rect.fromLTRB(25, 250, 100, 300); - const margin = EdgeInsets.only(right: 10); - expect( - rect.applyMargin(margin).center, - Offset( - rect.center.dx - 10, - rect.center.dy, - ), - ); - }); - - test('should move rect the correct amount with left padding', () { - const rect = Rect.fromLTRB(25, 250, 100, 300); - const margin = EdgeInsets.only(left: 10); - expect( - rect.applyMargin(margin).center, - Offset( - rect.center.dx + 10, - rect.center.dy, - ), - ); - }); - - test('should move rect the correct amount with bottom padding', () { - const rect = Rect.fromLTRB(25, 250, 100, 300); - const margin = EdgeInsets.only(bottom: 10); - expect( - rect.applyMargin(margin).center, - Offset( - rect.center.dx, - rect.center.dy - 10, - ), - ); - }); - - test('should move rect the correct amount with top padding', () { - const rect = Rect.fromLTRB(25, 250, 100, 300); - const margin = EdgeInsets.only(top: 10); - expect( - rect.applyMargin(margin).center, - Offset( - rect.center.dx, - rect.center.dy + 10, - ), - ); - }); - }); }); } From 49d0a1f9fcbad6d17b3ec90442256b70b2114738 Mon Sep 17 00:00:00 2001 From: Jani Koponen Date: Sat, 2 Mar 2024 15:11:04 +0200 Subject: [PATCH 22/27] Regenerate mocks and add tests --- .../base/axis_chart/axis_chart_painter.dart | 4 + .../bar_chart_painter_test.mocks.dart | 2 +- .../bar_chart_renderer_test.mocks.dart | 33 +- .../line_chart/line_chart_painter_test.dart | 302 +++++++++++++++++- .../line_chart_painter_test.mocks.dart | 301 ++++++++++++++--- .../line_chart_renderer_test.mocks.dart | 33 +- .../pie_chart_painter_test.mocks.dart | 2 +- .../pie_chart_renderer_test.mocks.dart | 2 +- .../radar_chart_painter_test.mocks.dart | 2 +- .../radar_chart_renderer_test.mocks.dart | 2 +- .../scatter_chart_painter_test.mocks.dart | 2 +- .../scatter_chart_renderer_test.mocks.dart | 33 +- test/utils/canvas_wrapper_test.mocks.dart | 2 +- test/utils/utils_test.mocks.dart | 2 +- 14 files changed, 659 insertions(+), 63 deletions(-) diff --git a/lib/src/chart/base/axis_chart/axis_chart_painter.dart b/lib/src/chart/base/axis_chart/axis_chart_painter.dart index 64507ed4f..219971620 100644 --- a/lib/src/chart/base/axis_chart/axis_chart_painter.dart +++ b/lib/src/chart/base/axis_chart/axis_chart_painter.dart @@ -215,6 +215,7 @@ abstract class AxisChartPainter } } + @visibleForTesting void drawExtraLines( BuildContext context, CanvasWrapper canvasWrapper, @@ -233,6 +234,7 @@ abstract class AxisChartPainter } } + @visibleForTesting void drawHorizontalLines( BuildContext context, CanvasWrapper canvasWrapper, @@ -338,6 +340,7 @@ abstract class AxisChartPainter } } + @visibleForTesting void drawVerticalLines( BuildContext context, CanvasWrapper canvasWrapper, @@ -444,6 +447,7 @@ abstract class AxisChartPainter } } + @visibleForTesting void drawLineLabel( Color backgroundColor, Alignment alignment, diff --git a/test/chart/bar_chart/bar_chart_painter_test.mocks.dart b/test/chart/bar_chart/bar_chart_painter_test.mocks.dart index 7955d4248..df26fe5b0 100644 --- a/test/chart/bar_chart/bar_chart_painter_test.mocks.dart +++ b/test/chart/bar_chart/bar_chart_painter_test.mocks.dart @@ -1,4 +1,4 @@ -// Mocks generated by Mockito 5.4.3 from annotations +// Mocks generated by Mockito 5.4.4 from annotations // in fl_chart/test/chart/bar_chart/bar_chart_painter_test.dart. // Do not manually edit this file. diff --git a/test/chart/bar_chart/bar_chart_renderer_test.mocks.dart b/test/chart/bar_chart/bar_chart_renderer_test.mocks.dart index 432eda667..ff04e940f 100644 --- a/test/chart/bar_chart/bar_chart_renderer_test.mocks.dart +++ b/test/chart/bar_chart/bar_chart_renderer_test.mocks.dart @@ -1,4 +1,4 @@ -// Mocks generated by Mockito 5.4.3 from annotations +// Mocks generated by Mockito 5.4.4 from annotations // in fl_chart/test/chart/bar_chart/bar_chart_renderer_test.dart. // Do not manually edit this file. @@ -14,6 +14,7 @@ import 'package:fl_chart/src/utils/canvas_wrapper.dart' as _i11; import 'package:flutter/foundation.dart' as _i5; import 'package:flutter/gestures.dart' as _i8; import 'package:flutter/material.dart' as _i6; +import 'package:flutter/painting.dart' as _i14; import 'package:flutter/rendering.dart' as _i3; import 'package:flutter/src/rendering/layer.dart' as _i4; import 'package:flutter/src/widgets/notification_listener.dart' as _i9; @@ -1473,6 +1474,34 @@ class MockBarChartPainter extends _i1.Mock implements _i10.BarChartPainter { returnValueForMissingStub: null, ); + @override + void drawLineLabel( + _i2.Color? backgroundColor, + _i14.Alignment? alignment, + _i2.Rect? textArea, + _i14.EdgeInsets? padding, + double? verticalOffset, + double? horizontalOffset, + _i14.TextPainter? tp, + _i11.CanvasWrapper? canvasWrapper, + ) => + super.noSuchMethod( + Invocation.method( + #drawLineLabel, + [ + backgroundColor, + alignment, + textArea, + padding, + verticalOffset, + horizontalOffset, + tp, + canvasWrapper, + ], + ), + returnValueForMissingStub: null, + ); + @override double getPixelX( double? spotX, @@ -1515,7 +1544,7 @@ class MockBarChartPainter extends _i1.Mock implements _i10.BarChartPainter { double? tooltipWidth, _i13.FLHorizontalAlignment? tooltipHorizontalAlignment, double? tooltipHorizontalOffset, - _i6.EdgeInsets? tooltipPadding, + _i14.EdgeInsets? tooltipPadding, ) => (super.noSuchMethod( Invocation.method( diff --git a/test/chart/line_chart/line_chart_painter_test.dart b/test/chart/line_chart/line_chart_painter_test.dart index cb156a553..750fa5ae8 100644 --- a/test/chart/line_chart/line_chart_painter_test.dart +++ b/test/chart/line_chart/line_chart_painter_test.dart @@ -17,7 +17,13 @@ import 'package:mockito/mockito.dart'; import '../data_pool.dart'; import 'line_chart_painter_test.mocks.dart'; -@GenerateMocks([Canvas, CanvasWrapper, BuildContext, Utils, LineChartPainter]) +@GenerateNiceMocks([ + MockSpec(), + MockSpec(), + MockSpec(), + MockSpec(), + MockSpec(), +]) void main() { group('paint()', () { test('test 1', () { @@ -2291,6 +2297,300 @@ void main() { ), ); }); + + test('should not draw vertical label if show is false', () { + const viewSize = Size(100, 100); + + final data = LineChartData( + minY: -1, + maxY: 10, + minX: -1, + maxX: 10, + titlesData: const FlTitlesData(show: false), + extraLinesData: ExtraLinesData( + verticalLines: [ + VerticalLine( + x: 5, + color: Colors.white, + label: VerticalLineLabel( + show: false, + style: const TextStyle( + color: Colors.white, + fontSize: 10, + ), + ), + ), + ], + ), + ); + + final lineChartPainter = LineChartPainter(); + + final holder = + PaintHolder(data, data, TextScaler.noScaling); + final mockCanvasWrapper = MockCanvasWrapper(); + when(mockCanvasWrapper.size).thenAnswer((realInvocation) => viewSize); + when(mockCanvasWrapper.canvas).thenReturn(MockCanvas()); + + final mockBuildContext = MockBuildContext(); + + final results = >[]; + when( + mockCanvasWrapper.drawRect( + captureAny, + captureAny, + ), + ).thenAnswer((inv) { + results.add({ + 'rect': inv.positionalArguments[0] as Rect?, + 'paint': inv.positionalArguments[1] as Paint?, + }); + }); + + lineChartPainter.drawExtraLines( + mockBuildContext, + mockCanvasWrapper, + holder, + ); + + expect(results.length, 0); + }); + + test('should draw vertical label if show is true', () { + const viewSize = Size(100, 100); + + final data = LineChartData( + minY: -1, + maxY: 10, + minX: -1, + maxX: 10, + titlesData: const FlTitlesData(show: false), + extraLinesData: ExtraLinesData( + verticalLines: [ + VerticalLine( + x: 5, + color: Colors.white, + label: VerticalLineLabel( + show: false, + style: const TextStyle( + color: Colors.white, + fontSize: 10, + ), + ), + ), + ], + ), + ); + + final lineChartPainter = LineChartPainter(); + + final holder = + PaintHolder(data, data, TextScaler.noScaling); + final mockCanvasWrapper = MockCanvasWrapper(); + when(mockCanvasWrapper.size).thenAnswer((realInvocation) => viewSize); + when(mockCanvasWrapper.canvas).thenReturn(MockCanvas()); + + final mockBuildContext = MockBuildContext(); + + final results = >[]; + when( + mockCanvasWrapper.drawRect( + captureAny, + captureAny, + ), + ).thenAnswer((inv) { + results.add({ + 'rect': inv.positionalArguments[0] as Rect?, + 'paint': inv.positionalArguments[1] as Paint?, + }); + }); + + lineChartPainter.drawExtraLines( + mockBuildContext, + mockCanvasWrapper, + holder, + ); + + expect(results.length, 1); + }); + + test('should not draw horizontal label if show is false', () { + const viewSize = Size(100, 100); + + final data = LineChartData( + minY: -1, + maxY: 10, + minX: -1, + maxX: 10, + titlesData: const FlTitlesData(show: false), + extraLinesData: ExtraLinesData( + horizontalLines: [ + HorizontalLine( + y: 5, + color: Colors.white, + label: HorizontalLineLabel( + style: const TextStyle( + color: Colors.white, + fontSize: 10, + ), + ), + ), + ], + ), + ); + + final lineChartPainter = LineChartPainter(); + + final holder = + PaintHolder(data, data, TextScaler.noScaling); + final mockCanvasWrapper = MockCanvasWrapper(); + when(mockCanvasWrapper.size).thenAnswer((realInvocation) => viewSize); + when(mockCanvasWrapper.canvas).thenReturn(MockCanvas()); + + final mockBuildContext = MockBuildContext(); + + final results = >[]; + when( + mockCanvasWrapper.drawRect( + captureAny, + captureAny, + ), + ).thenAnswer((inv) { + results.add({ + 'rect': inv.positionalArguments[0] as Rect?, + 'paint': inv.positionalArguments[1] as Paint?, + }); + }); + + lineChartPainter.drawExtraLines( + mockBuildContext, + mockCanvasWrapper, + holder, + ); + + expect(results.length, 0); + }); + + test('should draw horizontal label if show is true', () { + const viewSize = Size(100, 100); + + final data = LineChartData( + minY: -1, + maxY: 10, + minX: -1, + maxX: 10, + titlesData: const FlTitlesData(show: false), + extraLinesData: ExtraLinesData( + horizontalLines: [ + HorizontalLine( + y: 5, + color: Colors.white, + label: HorizontalLineLabel( + show: true, + style: const TextStyle( + color: Colors.white, + fontSize: 10, + ), + ), + ), + ], + ), + ); + + final lineChartPainter = LineChartPainter(); + + final holder = + PaintHolder(data, data, TextScaler.noScaling); + final mockCanvasWrapper = MockCanvasWrapper(); + when(mockCanvasWrapper.size).thenAnswer((realInvocation) => viewSize); + when(mockCanvasWrapper.canvas).thenReturn(MockCanvas()); + + final mockBuildContext = MockBuildContext(); + + final results = >[]; + when( + mockCanvasWrapper.drawRect( + captureAny, + captureAny, + ), + ).thenAnswer((inv) { + results.add({ + 'rect': inv.positionalArguments[0] as Rect?, + 'paint': inv.positionalArguments[1] as Paint?, + }); + }); + + lineChartPainter.drawExtraLines( + mockBuildContext, + mockCanvasWrapper, + holder, + ); + + expect(results.length, 1); + }); + + test('verticalOffset should move horizontal line label', () { + const viewSize = Size(100, 100); + + final data = LineChartData( + minY: -1, + maxY: 10, + minX: -1, + maxX: 10, + titlesData: const FlTitlesData(show: false), + extraLinesData: ExtraLinesData( + horizontalLines: [ + HorizontalLine( + y: 5, + color: Colors.white, + label: HorizontalLineLabel( + verticalOffset: 10, + show: true, + style: const TextStyle( + color: Colors.white, + fontSize: 10, + ), + ), + ), + ], + ), + ); + + final lineChartPainter = LineChartPainter(); + + final holder = + PaintHolder(data, data, TextScaler.noScaling); + final mockCanvasWrapper = MockCanvasWrapper(); + when(mockCanvasWrapper.size).thenAnswer((realInvocation) => viewSize); + when(mockCanvasWrapper.canvas).thenReturn(MockCanvas()); + + final mockBuildContext = MockBuildContext(); + + final results = >[]; + when( + mockCanvasWrapper.drawRect( + captureAny, + captureAny, + ), + ).thenAnswer((inv) { + results.add({ + 'rect': inv.positionalArguments[0] as Rect?, + 'paint': inv.positionalArguments[1] as Paint?, + }); + }); + + lineChartPainter.drawExtraLines( + mockBuildContext, + mockCanvasWrapper, + holder, + ); + + expect(results.length, 1); + + final rect = results[0]['rect'] as Rect; + + expect(rect, const Rect.fromLTRB(0, 25.5, 30, 35.5)); // Fix test + }); }); group('drawTouchTooltip()', () { diff --git a/test/chart/line_chart/line_chart_painter_test.mocks.dart b/test/chart/line_chart/line_chart_painter_test.mocks.dart index 9526532b4..fe218f82b 100644 --- a/test/chart/line_chart/line_chart_painter_test.mocks.dart +++ b/test/chart/line_chart/line_chart_painter_test.mocks.dart @@ -1,4 +1,4 @@ -// Mocks generated by Mockito 5.4.3 from annotations +// Mocks generated by Mockito 5.4.4 from annotations // in fl_chart/test/chart/line_chart/line_chart_painter_test.dart. // Do not manually edit this file. @@ -14,7 +14,6 @@ import 'package:fl_chart/src/utils/canvas_wrapper.dart' as _i6; import 'package:fl_chart/src/utils/utils.dart' as _i8; import 'package:flutter/cupertino.dart' as _i3; import 'package:flutter/foundation.dart' as _i4; -import 'package:flutter/material.dart' as _i11; import 'package:mockito/mockito.dart' as _i1; import 'package:mockito/src/dummies.dart' as _i9; @@ -160,10 +159,6 @@ class _FakePath_9 extends _i1.SmartFake implements _i2.Path { /// /// See the documentation for Mockito's code generation for more information. class MockCanvas extends _i1.Mock implements _i2.Canvas { - MockCanvas() { - _i1.throwOnMissingStub(this); - } - @override void save() => super.noSuchMethod( Invocation.method( @@ -214,6 +209,7 @@ class MockCanvas extends _i1.Mock implements _i2.Canvas { [], ), returnValue: 0, + returnValueForMissingStub: 0, ) as int); @override @@ -289,6 +285,7 @@ class MockCanvas extends _i1.Mock implements _i2.Canvas { [], ), returnValue: _i5.Float64List(0), + returnValueForMissingStub: _i5.Float64List(0), ) as _i5.Float64List); @override @@ -350,6 +347,13 @@ class MockCanvas extends _i1.Mock implements _i2.Canvas { [], ), ), + returnValueForMissingStub: _FakeRect_0( + this, + Invocation.method( + #getLocalClipBounds, + [], + ), + ), ) as _i2.Rect); @override @@ -365,6 +369,13 @@ class MockCanvas extends _i1.Mock implements _i2.Canvas { [], ), ), + returnValueForMissingStub: _FakeRect_0( + this, + Invocation.method( + #getDestinationClipBounds, + [], + ), + ), ) as _i2.Rect); @override @@ -746,10 +757,6 @@ class MockCanvas extends _i1.Mock implements _i2.Canvas { /// /// See the documentation for Mockito's code generation for more information. class MockCanvasWrapper extends _i1.Mock implements _i6.CanvasWrapper { - MockCanvasWrapper() { - _i1.throwOnMissingStub(this); - } - @override _i2.Canvas get canvas => (super.noSuchMethod( Invocation.getter(#canvas), @@ -757,6 +764,10 @@ class MockCanvasWrapper extends _i1.Mock implements _i6.CanvasWrapper { this, Invocation.getter(#canvas), ), + returnValueForMissingStub: _FakeCanvas_1( + this, + Invocation.getter(#canvas), + ), ) as _i2.Canvas); @override @@ -766,6 +777,10 @@ class MockCanvasWrapper extends _i1.Mock implements _i6.CanvasWrapper { this, Invocation.getter(#size), ), + returnValueForMissingStub: _FakeSize_2( + this, + Invocation.getter(#size), + ), ) as _i2.Size); @override @@ -1076,10 +1091,6 @@ class MockCanvasWrapper extends _i1.Mock implements _i6.CanvasWrapper { /// /// See the documentation for Mockito's code generation for more information. class MockBuildContext extends _i1.Mock implements _i3.BuildContext { - MockBuildContext() { - _i1.throwOnMissingStub(this); - } - @override _i3.Widget get widget => (super.noSuchMethod( Invocation.getter(#widget), @@ -1087,18 +1098,24 @@ class MockBuildContext extends _i1.Mock implements _i3.BuildContext { this, Invocation.getter(#widget), ), + returnValueForMissingStub: _FakeWidget_3( + this, + Invocation.getter(#widget), + ), ) as _i3.Widget); @override bool get mounted => (super.noSuchMethod( Invocation.getter(#mounted), returnValue: false, + returnValueForMissingStub: false, ) as bool); @override bool get debugDoingBuild => (super.noSuchMethod( Invocation.getter(#debugDoingBuild), returnValue: false, + returnValueForMissingStub: false, ) as bool); @override @@ -1120,6 +1137,14 @@ class MockBuildContext extends _i1.Mock implements _i3.BuildContext { {#aspect: aspect}, ), ), + returnValueForMissingStub: _FakeInheritedWidget_4( + this, + Invocation.method( + #dependOnInheritedElement, + [ancestor], + {#aspect: aspect}, + ), + ), ) as _i3.InheritedWidget); @override @@ -1170,6 +1195,14 @@ class MockBuildContext extends _i1.Mock implements _i3.BuildContext { {#style: style}, ), ), + returnValueForMissingStub: _FakeDiagnosticsNode_5( + this, + Invocation.method( + #describeElement, + [name], + {#style: style}, + ), + ), ) as _i3.DiagnosticsNode); @override @@ -1191,6 +1224,14 @@ class MockBuildContext extends _i1.Mock implements _i3.BuildContext { {#style: style}, ), ), + returnValueForMissingStub: _FakeDiagnosticsNode_5( + this, + Invocation.method( + #describeWidget, + [name], + {#style: style}, + ), + ), ) as _i3.DiagnosticsNode); @override @@ -1203,6 +1244,7 @@ class MockBuildContext extends _i1.Mock implements _i3.BuildContext { {#expectedAncestorType: expectedAncestorType}, ), returnValue: <_i3.DiagnosticsNode>[], + returnValueForMissingStub: <_i3.DiagnosticsNode>[], ) as List<_i3.DiagnosticsNode>); @override @@ -1219,6 +1261,13 @@ class MockBuildContext extends _i1.Mock implements _i3.BuildContext { [name], ), ), + returnValueForMissingStub: _FakeDiagnosticsNode_5( + this, + Invocation.method( + #describeOwnershipChain, + [name], + ), + ), ) as _i3.DiagnosticsNode); } @@ -1226,10 +1275,6 @@ class MockBuildContext extends _i1.Mock implements _i3.BuildContext { /// /// See the documentation for Mockito's code generation for more information. class MockUtils extends _i1.Mock implements _i8.Utils { - MockUtils() { - _i1.throwOnMissingStub(this); - } - @override double radians(double? degrees) => (super.noSuchMethod( Invocation.method( @@ -1237,6 +1282,7 @@ class MockUtils extends _i1.Mock implements _i8.Utils { [degrees], ), returnValue: 0.0, + returnValueForMissingStub: 0.0, ) as double); @override @@ -1246,6 +1292,7 @@ class MockUtils extends _i1.Mock implements _i8.Utils { [radians], ), returnValue: 0.0, + returnValueForMissingStub: 0.0, ) as double); @override @@ -1261,6 +1308,13 @@ class MockUtils extends _i1.Mock implements _i8.Utils { [screenSize], ), ), + returnValueForMissingStub: _FakeSize_2( + this, + Invocation.method( + #getDefaultSize, + [screenSize], + ), + ), ) as _i2.Size); @override @@ -1277,6 +1331,7 @@ class MockUtils extends _i1.Mock implements _i8.Utils { ], ), returnValue: 0.0, + returnValueForMissingStub: 0.0, ) as double); @override @@ -1302,6 +1357,16 @@ class MockUtils extends _i1.Mock implements _i8.Utils { ], ), ), + returnValueForMissingStub: _FakeOffset_6( + this, + Invocation.method( + #calculateRotationOffset, + [ + size, + degree, + ], + ), + ), ) as _i2.Offset); @override @@ -1309,13 +1374,16 @@ class MockUtils extends _i1.Mock implements _i8.Utils { _i3.BorderRadius? borderRadius, double? width, ) => - (super.noSuchMethod(Invocation.method( - #normalizeBorderRadius, - [ - borderRadius, - width, - ], - )) as _i3.BorderRadius?); + (super.noSuchMethod( + Invocation.method( + #normalizeBorderRadius, + [ + borderRadius, + width, + ], + ), + returnValueForMissingStub: null, + ) as _i3.BorderRadius?); @override _i3.BorderSide normalizeBorderSide( @@ -1340,6 +1408,16 @@ class MockUtils extends _i1.Mock implements _i8.Utils { ], ), ), + returnValueForMissingStub: _FakeBorderSide_7( + this, + Invocation.method( + #normalizeBorderSide, + [ + borderSide, + width, + ], + ), + ), ) as _i3.BorderSide); @override @@ -1358,6 +1436,7 @@ class MockUtils extends _i1.Mock implements _i8.Utils { {#pixelPerInterval: pixelPerInterval}, ), returnValue: 0.0, + returnValueForMissingStub: 0.0, ) as double); @override @@ -1367,6 +1446,7 @@ class MockUtils extends _i1.Mock implements _i8.Utils { [input], ), returnValue: 0.0, + returnValueForMissingStub: 0.0, ) as double); @override @@ -1376,6 +1456,7 @@ class MockUtils extends _i1.Mock implements _i8.Utils { [value], ), returnValue: 0, + returnValueForMissingStub: 0, ) as int); @override @@ -1404,6 +1485,17 @@ class MockUtils extends _i1.Mock implements _i8.Utils { ], ), ), + returnValueForMissingStub: _i9.dummyValue( + this, + Invocation.method( + #formatNumber, + [ + axisMin, + axisMax, + axisValue, + ], + ), + ), ) as String); @override @@ -1429,6 +1521,16 @@ class MockUtils extends _i1.Mock implements _i8.Utils { ], ), ), + returnValueForMissingStub: _FakeTextStyle_8( + this, + Invocation.method( + #getThemeAwareTextStyle, + [ + context, + providedStyle, + ], + ), + ), ) as _i3.TextStyle); @override @@ -1449,6 +1551,7 @@ class MockUtils extends _i1.Mock implements _i8.Utils { {#baseline: baseline}, ), returnValue: 0.0, + returnValueForMissingStub: 0.0, ) as double); @override @@ -1458,6 +1561,7 @@ class MockUtils extends _i1.Mock implements _i8.Utils { [radius], ), returnValue: 0.0, + returnValueForMissingStub: 0.0, ) as double); } @@ -1465,10 +1569,6 @@ class MockUtils extends _i1.Mock implements _i8.Utils { /// /// See the documentation for Mockito's code generation for more information. class MockLineChartPainter extends _i1.Mock implements _i10.LineChartPainter { - MockLineChartPainter() { - _i1.throwOnMissingStub(this); - } - @override void paint( _i3.BuildContext? context, @@ -1609,6 +1709,19 @@ class MockLineChartPainter extends _i1.Mock implements _i10.LineChartPainter { {#appendToPath: appendToPath}, ), ), + returnValueForMissingStub: _FakePath_9( + this, + Invocation.method( + #generateBarPath, + [ + viewSize, + barData, + barSpots, + holder, + ], + {#appendToPath: appendToPath}, + ), + ), ) as _i2.Path); @override @@ -1643,6 +1756,19 @@ class MockLineChartPainter extends _i1.Mock implements _i10.LineChartPainter { {#appendToPath: appendToPath}, ), ), + returnValueForMissingStub: _FakePath_9( + this, + Invocation.method( + #generateNormalBarPath, + [ + viewSize, + barData, + barSpots, + holder, + ], + {#appendToPath: appendToPath}, + ), + ), ) as _i2.Path); @override @@ -1677,6 +1803,19 @@ class MockLineChartPainter extends _i1.Mock implements _i10.LineChartPainter { {#appendToPath: appendToPath}, ), ), + returnValueForMissingStub: _FakePath_9( + this, + Invocation.method( + #generateStepBarPath, + [ + viewSize, + barData, + barSpots, + holder, + ], + {#appendToPath: appendToPath}, + ), + ), ) as _i2.Path); @override @@ -1714,6 +1853,20 @@ class MockLineChartPainter extends _i1.Mock implements _i10.LineChartPainter { {#fillCompletely: fillCompletely}, ), ), + returnValueForMissingStub: _FakePath_9( + this, + Invocation.method( + #generateBelowBarPath, + [ + viewSize, + barData, + barPath, + barSpots, + holder, + ], + {#fillCompletely: fillCompletely}, + ), + ), ) as _i2.Path); @override @@ -1751,6 +1904,20 @@ class MockLineChartPainter extends _i1.Mock implements _i10.LineChartPainter { {#fillCompletely: fillCompletely}, ), ), + returnValueForMissingStub: _FakePath_9( + this, + Invocation.method( + #generateAboveBarPath, + [ + viewSize, + barData, + barPath, + barSpots, + holder, + ], + {#fillCompletely: fillCompletely}, + ), + ), ) as _i2.Path); @override @@ -1897,6 +2064,7 @@ class MockLineChartPainter extends _i1.Mock implements _i10.LineChartPainter { ], ), returnValue: 0.0, + returnValueForMissingStub: 0.0, ) as double); @override @@ -1905,14 +2073,17 @@ class MockLineChartPainter extends _i1.Mock implements _i10.LineChartPainter { _i2.Size? size, _i11.PaintHolder<_i7.LineChartData>? holder, ) => - (super.noSuchMethod(Invocation.method( - #handleTouch, - [ - localPosition, - size, - holder, - ], - )) as List<_i7.TouchLineBarSpot>?); + (super.noSuchMethod( + Invocation.method( + #handleTouch, + [ + localPosition, + size, + holder, + ], + ), + returnValueForMissingStub: null, + ) as List<_i7.TouchLineBarSpot>?); @override _i7.TouchLineBarSpot? getNearestTouchedSpot( @@ -1922,16 +2093,19 @@ class MockLineChartPainter extends _i1.Mock implements _i10.LineChartPainter { int? barDataPosition, _i11.PaintHolder<_i7.LineChartData>? holder, ) => - (super.noSuchMethod(Invocation.method( - #getNearestTouchedSpot, - [ - viewSize, - touchedPoint, - barData, - barDataPosition, - holder, - ], - )) as _i7.TouchLineBarSpot?); + (super.noSuchMethod( + Invocation.method( + #getNearestTouchedSpot, + [ + viewSize, + touchedPoint, + barData, + barDataPosition, + holder, + ], + ), + returnValueForMissingStub: null, + ) as _i7.TouchLineBarSpot?); @override void drawGrid( @@ -2039,6 +2213,34 @@ class MockLineChartPainter extends _i1.Mock implements _i10.LineChartPainter { returnValueForMissingStub: null, ); + @override + void drawLineLabel( + _i2.Color? backgroundColor, + _i3.Alignment? alignment, + _i2.Rect? textArea, + _i3.EdgeInsets? padding, + double? verticalOffset, + double? horizontalOffset, + _i3.TextPainter? tp, + _i6.CanvasWrapper? canvasWrapper, + ) => + super.noSuchMethod( + Invocation.method( + #drawLineLabel, + [ + backgroundColor, + alignment, + textArea, + padding, + verticalOffset, + horizontalOffset, + tp, + canvasWrapper, + ], + ), + returnValueForMissingStub: null, + ); + @override double getPixelX( double? spotX, @@ -2055,6 +2257,7 @@ class MockLineChartPainter extends _i1.Mock implements _i10.LineChartPainter { ], ), returnValue: 0.0, + returnValueForMissingStub: 0.0, ) as double); @override @@ -2073,6 +2276,7 @@ class MockLineChartPainter extends _i1.Mock implements _i10.LineChartPainter { ], ), returnValue: 0.0, + returnValueForMissingStub: 0.0, ) as double); @override @@ -2081,7 +2285,7 @@ class MockLineChartPainter extends _i1.Mock implements _i10.LineChartPainter { double? tooltipWidth, _i7.FLHorizontalAlignment? tooltipHorizontalAlignment, double? tooltipHorizontalOffset, - _i11.EdgeInsets? tooltipPadding, + _i3.EdgeInsets? tooltipPadding, ) => (super.noSuchMethod( Invocation.method( @@ -2095,5 +2299,6 @@ class MockLineChartPainter extends _i1.Mock implements _i10.LineChartPainter { ], ), returnValue: 0.0, + returnValueForMissingStub: 0.0, ) as double); } diff --git a/test/chart/line_chart/line_chart_renderer_test.mocks.dart b/test/chart/line_chart/line_chart_renderer_test.mocks.dart index 7db351bef..cc108cc70 100644 --- a/test/chart/line_chart/line_chart_renderer_test.mocks.dart +++ b/test/chart/line_chart/line_chart_renderer_test.mocks.dart @@ -1,4 +1,4 @@ -// Mocks generated by Mockito 5.4.3 from annotations +// Mocks generated by Mockito 5.4.4 from annotations // in fl_chart/test/chart/line_chart/line_chart_renderer_test.dart. // Do not manually edit this file. @@ -14,6 +14,7 @@ import 'package:fl_chart/src/utils/canvas_wrapper.dart' as _i11; import 'package:flutter/foundation.dart' as _i5; import 'package:flutter/gestures.dart' as _i8; import 'package:flutter/material.dart' as _i6; +import 'package:flutter/painting.dart' as _i14; import 'package:flutter/rendering.dart' as _i3; import 'package:flutter/src/rendering/layer.dart' as _i4; import 'package:flutter/src/widgets/notification_listener.dart' as _i9; @@ -1820,6 +1821,34 @@ class MockLineChartPainter extends _i1.Mock implements _i10.LineChartPainter { returnValueForMissingStub: null, ); + @override + void drawLineLabel( + _i2.Color? backgroundColor, + _i14.Alignment? alignment, + _i2.Rect? textArea, + _i14.EdgeInsets? padding, + double? verticalOffset, + double? horizontalOffset, + _i14.TextPainter? tp, + _i11.CanvasWrapper? canvasWrapper, + ) => + super.noSuchMethod( + Invocation.method( + #drawLineLabel, + [ + backgroundColor, + alignment, + textArea, + padding, + verticalOffset, + horizontalOffset, + tp, + canvasWrapper, + ], + ), + returnValueForMissingStub: null, + ); + @override double getPixelX( double? spotX, @@ -1862,7 +1891,7 @@ class MockLineChartPainter extends _i1.Mock implements _i10.LineChartPainter { double? tooltipWidth, _i13.FLHorizontalAlignment? tooltipHorizontalAlignment, double? tooltipHorizontalOffset, - _i6.EdgeInsets? tooltipPadding, + _i14.EdgeInsets? tooltipPadding, ) => (super.noSuchMethod( Invocation.method( diff --git a/test/chart/pie_chart/pie_chart_painter_test.mocks.dart b/test/chart/pie_chart/pie_chart_painter_test.mocks.dart index 14289e27d..7d8f5da1b 100644 --- a/test/chart/pie_chart/pie_chart_painter_test.mocks.dart +++ b/test/chart/pie_chart/pie_chart_painter_test.mocks.dart @@ -1,4 +1,4 @@ -// Mocks generated by Mockito 5.4.3 from annotations +// Mocks generated by Mockito 5.4.4 from annotations // in fl_chart/test/chart/pie_chart/pie_chart_painter_test.dart. // Do not manually edit this file. diff --git a/test/chart/pie_chart/pie_chart_renderer_test.mocks.dart b/test/chart/pie_chart/pie_chart_renderer_test.mocks.dart index 98ce2bab9..72aff7d65 100644 --- a/test/chart/pie_chart/pie_chart_renderer_test.mocks.dart +++ b/test/chart/pie_chart/pie_chart_renderer_test.mocks.dart @@ -1,4 +1,4 @@ -// Mocks generated by Mockito 5.4.3 from annotations +// Mocks generated by Mockito 5.4.4 from annotations // in fl_chart/test/chart/pie_chart/pie_chart_renderer_test.dart. // Do not manually edit this file. diff --git a/test/chart/radar_chart/radar_chart_painter_test.mocks.dart b/test/chart/radar_chart/radar_chart_painter_test.mocks.dart index c25bff9ce..006245d2d 100644 --- a/test/chart/radar_chart/radar_chart_painter_test.mocks.dart +++ b/test/chart/radar_chart/radar_chart_painter_test.mocks.dart @@ -1,4 +1,4 @@ -// Mocks generated by Mockito 5.4.3 from annotations +// Mocks generated by Mockito 5.4.4 from annotations // in fl_chart/test/chart/radar_chart/radar_chart_painter_test.dart. // Do not manually edit this file. diff --git a/test/chart/radar_chart/radar_chart_renderer_test.mocks.dart b/test/chart/radar_chart/radar_chart_renderer_test.mocks.dart index d5559d87d..d79d0a49d 100644 --- a/test/chart/radar_chart/radar_chart_renderer_test.mocks.dart +++ b/test/chart/radar_chart/radar_chart_renderer_test.mocks.dart @@ -1,4 +1,4 @@ -// Mocks generated by Mockito 5.4.3 from annotations +// Mocks generated by Mockito 5.4.4 from annotations // in fl_chart/test/chart/radar_chart/radar_chart_renderer_test.dart. // Do not manually edit this file. diff --git a/test/chart/scatter_chart/scatter_chart_painter_test.mocks.dart b/test/chart/scatter_chart/scatter_chart_painter_test.mocks.dart index 7ebd21827..a325f8927 100644 --- a/test/chart/scatter_chart/scatter_chart_painter_test.mocks.dart +++ b/test/chart/scatter_chart/scatter_chart_painter_test.mocks.dart @@ -1,4 +1,4 @@ -// Mocks generated by Mockito 5.4.3 from annotations +// Mocks generated by Mockito 5.4.4 from annotations // in fl_chart/test/chart/scatter_chart/scatter_chart_painter_test.dart. // Do not manually edit this file. diff --git a/test/chart/scatter_chart/scatter_chart_renderer_test.mocks.dart b/test/chart/scatter_chart/scatter_chart_renderer_test.mocks.dart index 708dbf51f..c38776a12 100644 --- a/test/chart/scatter_chart/scatter_chart_renderer_test.mocks.dart +++ b/test/chart/scatter_chart/scatter_chart_renderer_test.mocks.dart @@ -1,4 +1,4 @@ -// Mocks generated by Mockito 5.4.3 from annotations +// Mocks generated by Mockito 5.4.4 from annotations // in fl_chart/test/chart/scatter_chart/scatter_chart_renderer_test.dart. // Do not manually edit this file. @@ -15,6 +15,7 @@ import 'package:fl_chart/src/utils/canvas_wrapper.dart' as _i11; import 'package:flutter/foundation.dart' as _i5; import 'package:flutter/gestures.dart' as _i8; import 'package:flutter/material.dart' as _i6; +import 'package:flutter/painting.dart' as _i14; import 'package:flutter/rendering.dart' as _i3; import 'package:flutter/src/rendering/layer.dart' as _i4; import 'package:flutter/src/widgets/notification_listener.dart' as _i9; @@ -1439,6 +1440,34 @@ class MockScatterChartPainter extends _i1.Mock returnValueForMissingStub: null, ); + @override + void drawLineLabel( + _i2.Color? backgroundColor, + _i14.Alignment? alignment, + _i2.Rect? textArea, + _i14.EdgeInsets? padding, + double? verticalOffset, + double? horizontalOffset, + _i14.TextPainter? tp, + _i11.CanvasWrapper? canvasWrapper, + ) => + super.noSuchMethod( + Invocation.method( + #drawLineLabel, + [ + backgroundColor, + alignment, + textArea, + padding, + verticalOffset, + horizontalOffset, + tp, + canvasWrapper, + ], + ), + returnValueForMissingStub: null, + ); + @override double getPixelX( double? spotX, @@ -1481,7 +1510,7 @@ class MockScatterChartPainter extends _i1.Mock double? tooltipWidth, _i13.FLHorizontalAlignment? tooltipHorizontalAlignment, double? tooltipHorizontalOffset, - _i6.EdgeInsets? tooltipPadding, + _i14.EdgeInsets? tooltipPadding, ) => (super.noSuchMethod( Invocation.method( diff --git a/test/utils/canvas_wrapper_test.mocks.dart b/test/utils/canvas_wrapper_test.mocks.dart index e3f4a2964..94bfa1040 100644 --- a/test/utils/canvas_wrapper_test.mocks.dart +++ b/test/utils/canvas_wrapper_test.mocks.dart @@ -1,4 +1,4 @@ -// Mocks generated by Mockito 5.4.3 from annotations +// Mocks generated by Mockito 5.4.4 from annotations // in fl_chart/test/utils/canvas_wrapper_test.dart. // Do not manually edit this file. diff --git a/test/utils/utils_test.mocks.dart b/test/utils/utils_test.mocks.dart index 90fcd8b7a..7f2956778 100644 --- a/test/utils/utils_test.mocks.dart +++ b/test/utils/utils_test.mocks.dart @@ -1,4 +1,4 @@ -// Mocks generated by Mockito 5.4.3 from annotations +// Mocks generated by Mockito 5.4.4 from annotations // in fl_chart/test/utils/utils_test.dart. // Do not manually edit this file. From 7433c3e64225506f0e50d11f037774c2eb58d370 Mon Sep 17 00:00:00 2001 From: Jani Koponen Date: Sun, 3 Mar 2024 20:02:22 +0200 Subject: [PATCH 23/27] Add equal rect helper method --- test/helper_methods.dart | 20 ++++++++++++++++++++ 1 file changed, 20 insertions(+) diff --git a/test/helper_methods.dart b/test/helper_methods.dart index 1a2130ff0..6c31d46e7 100644 --- a/test/helper_methods.dart +++ b/test/helper_methods.dart @@ -45,6 +45,26 @@ class HelperMethods { return true; } + static bool equalsRects(Rect rect1, Rect rect2, {double tolerance = 0.05}) { + if ((rect1.left - rect2.left).abs() > tolerance) { + return false; + } + + if ((rect1.top - rect2.top).abs() > tolerance) { + return false; + } + + if ((rect1.right - rect2.right).abs() > tolerance) { + return false; + } + + if ((rect1.bottom - rect2.bottom).abs() > tolerance) { + return false; + } + + return true; + } + static bool equalsRRects( RRect rrect1, RRect rrect2, { From 08bfa4d4d3d1f1088bde628292225811983fc1df Mon Sep 17 00:00:00 2001 From: Jani Koponen Date: Sun, 3 Mar 2024 20:02:48 +0200 Subject: [PATCH 24/27] Add tests for vertical / horizontal line labels --- .../line_chart/line_chart_painter_test.dart | 656 +++++++++++++++++- 1 file changed, 653 insertions(+), 3 deletions(-) diff --git a/test/chart/line_chart/line_chart_painter_test.dart b/test/chart/line_chart/line_chart_painter_test.dart index 750fa5ae8..c7b87215e 100644 --- a/test/chart/line_chart/line_chart_painter_test.dart +++ b/test/chart/line_chart/line_chart_painter_test.dart @@ -14,6 +14,7 @@ import 'package:flutter_test/flutter_test.dart'; import 'package:mockito/annotations.dart'; import 'package:mockito/mockito.dart'; +import '../../helper_methods.dart'; import '../data_pool.dart'; import 'line_chart_painter_test.mocks.dart'; @@ -2297,7 +2298,9 @@ void main() { ), ); }); + }); + group('drawExtraLines() - labels', () { test('should not draw vertical label if show is false', () { const viewSize = Size(100, 100); @@ -2371,7 +2374,7 @@ void main() { x: 5, color: Colors.white, label: VerticalLineLabel( - show: false, + show: true, style: const TextStyle( color: Colors.white, fontSize: 10, @@ -2529,7 +2532,7 @@ void main() { expect(results.length, 1); }); - test('verticalOffset should move horizontal line label', () { + test('verticalOffset should move horizontal line label - 1', () { const viewSize = Size(100, 100); final data = LineChartData( @@ -2558,6 +2561,290 @@ void main() { final lineChartPainter = LineChartPainter(); + final holder = + PaintHolder(data, data, TextScaler.noScaling); + final mockCanvasWrapper = MockCanvasWrapper(); + + when(mockCanvasWrapper.size).thenAnswer((realInvocation) => viewSize); + when(mockCanvasWrapper.canvas).thenReturn(MockCanvas()); + + final mockBuildContext = MockBuildContext(); + + Rect? rect; + + when( + mockCanvasWrapper.drawRect( + captureAny, + captureAny, + ), + ).thenAnswer((inv) { + rect = inv.positionalArguments[0] as Rect?; + }); + + lineChartPainter.drawExtraLines( + mockBuildContext, + mockCanvasWrapper, + holder, + ); + + expect(rect != null, true, reason: 'Expected that Rect is not null'); + + const expected = Rect.fromLTRB(0, 21.5, 42, 35.5); + + expect( + HelperMethods.equalsRects( + rect!, + expected, + ), + true, + reason: 'expected $rect to equal $expected', + ); + }); + + test('verticalOffset should move horizontal line label - 2', () { + const viewSize = Size(100, 100); + + final data = LineChartData( + minY: -1, + maxY: 10, + minX: -1, + maxX: 10, + titlesData: const FlTitlesData(show: false), + extraLinesData: ExtraLinesData( + horizontalLines: [ + HorizontalLine( + y: 5, + color: Colors.white, + label: HorizontalLineLabel( + verticalOffset: -10, + show: true, + style: const TextStyle( + color: Colors.white, + fontSize: 10, + ), + ), + ), + ], + ), + ); + + final lineChartPainter = LineChartPainter(); + + final holder = + PaintHolder(data, data, TextScaler.noScaling); + final mockCanvasWrapper = MockCanvasWrapper(); + when(mockCanvasWrapper.size).thenAnswer((realInvocation) => viewSize); + when(mockCanvasWrapper.canvas).thenReturn(MockCanvas()); + + final mockBuildContext = MockBuildContext(); + + final results = >[]; + when( + mockCanvasWrapper.drawRect( + captureAny, + captureAny, + ), + ).thenAnswer((inv) { + results.add({ + 'rect': inv.positionalArguments[0] as Rect?, + 'paint': inv.positionalArguments[1] as Paint?, + }); + }); + + lineChartPainter.drawExtraLines( + mockBuildContext, + mockCanvasWrapper, + holder, + ); + + expect(results.length, 1); + + final rect = results[0]['rect'] as Rect; + + const expected = Rect.fromLTRB(0, 41.5, 42, 55.5); + + expect( + HelperMethods.equalsRects( + rect, + expected, + ), + true, + reason: 'expected $rect to equal $expected', + ); + }); + + test('horizontalOffset should move horizontal line label - 3', () { + const viewSize = Size(100, 100); + + final data = LineChartData( + minY: -1, + maxY: 10, + minX: -1, + maxX: 10, + titlesData: const FlTitlesData(show: false), + extraLinesData: ExtraLinesData( + horizontalLines: [ + HorizontalLine( + y: 5, + color: Colors.white, + label: HorizontalLineLabel( + horizontalOffset: 10, + show: true, + style: const TextStyle( + color: Colors.white, + fontSize: 10, + ), + ), + ), + ], + ), + ); + + final lineChartPainter = LineChartPainter(); + + final holder = + PaintHolder(data, data, TextScaler.noScaling); + final mockCanvasWrapper = MockCanvasWrapper(); + when(mockCanvasWrapper.size).thenAnswer((realInvocation) => viewSize); + when(mockCanvasWrapper.canvas).thenReturn(MockCanvas()); + + final mockBuildContext = MockBuildContext(); + + final results = >[]; + when( + mockCanvasWrapper.drawRect( + captureAny, + captureAny, + ), + ).thenAnswer((inv) { + results.add({ + 'rect': inv.positionalArguments[0] as Rect?, + 'paint': inv.positionalArguments[1] as Paint?, + }); + }); + + lineChartPainter.drawExtraLines( + mockBuildContext, + mockCanvasWrapper, + holder, + ); + + expect(results.length, 1); + + final rect = results[0]['rect'] as Rect; + + const expected = Rect.fromLTRB(10, 31.5, 52, 45.5); + + expect( + HelperMethods.equalsRects( + rect, + expected, + ), + true, + reason: 'expected $rect to equal $expected', + ); + }); + + test('horizontalOffset should move horizontal line label - 4', () { + const viewSize = Size(100, 100); + + final data = LineChartData( + minY: -1, + maxY: 10, + minX: -1, + maxX: 10, + titlesData: const FlTitlesData(show: false), + extraLinesData: ExtraLinesData( + horizontalLines: [ + HorizontalLine( + y: 5, + color: Colors.white, + label: HorizontalLineLabel( + horizontalOffset: -10, + show: true, + style: const TextStyle( + color: Colors.white, + fontSize: 10, + ), + ), + ), + ], + ), + ); + + final lineChartPainter = LineChartPainter(); + + final holder = + PaintHolder(data, data, TextScaler.noScaling); + final mockCanvasWrapper = MockCanvasWrapper(); + when(mockCanvasWrapper.size).thenAnswer((realInvocation) => viewSize); + when(mockCanvasWrapper.canvas).thenReturn(MockCanvas()); + + final mockBuildContext = MockBuildContext(); + + final results = >[]; + when( + mockCanvasWrapper.drawRect( + captureAny, + captureAny, + ), + ).thenAnswer((inv) { + results.add({ + 'rect': inv.positionalArguments[0] as Rect?, + 'paint': inv.positionalArguments[1] as Paint?, + }); + }); + + lineChartPainter.drawExtraLines( + mockBuildContext, + mockCanvasWrapper, + holder, + ); + + expect(results.length, 1); + + final rect = results[0]['rect'] as Rect; + + const expected = Rect.fromLTRB(-10, 31.5, 32, 45.5); + expect( + HelperMethods.equalsRects( + rect, + expected, + ), + true, + reason: 'expected $rect to equal $expected', + ); + }); + + test('verticalOffset should move vertical line label - 5', () { + const viewSize = Size(100, 100); + + final data = LineChartData( + minY: -1, + maxY: 10, + minX: -1, + maxX: 10, + titlesData: const FlTitlesData(show: false), + extraLinesData: ExtraLinesData( + verticalLines: [ + VerticalLine( + x: 5, + color: Colors.white, + label: VerticalLineLabel( + verticalOffset: -10, + show: true, + style: const TextStyle( + color: Colors.white, + fontSize: 10, + ), + ), + ), + ], + ), + ); + + final lineChartPainter = LineChartPainter(); + final holder = PaintHolder(data, data, TextScaler.noScaling); final mockCanvasWrapper = MockCanvasWrapper(); @@ -2589,7 +2876,370 @@ void main() { final rect = results[0]['rect'] as Rect; - expect(rect, const Rect.fromLTRB(0, 25.5, 30, 35.5)); // Fix test + const expected = Rect.fromLTRB(54.5, 110, 96.5, 124); + expect( + HelperMethods.equalsRects( + rect, + expected, + ), + true, + reason: 'expected $rect to equal $expected', + ); + }); + + test('verticalOffset should move vertical line label - 6', () { + const viewSize = Size(100, 100); + + final data = LineChartData( + minY: -1, + maxY: 10, + minX: -1, + maxX: 10, + titlesData: const FlTitlesData(show: false), + extraLinesData: ExtraLinesData( + verticalLines: [ + VerticalLine( + x: 5, + color: Colors.white, + label: VerticalLineLabel( + verticalOffset: 10, + show: true, + style: const TextStyle( + color: Colors.white, + fontSize: 10, + ), + ), + ), + ], + ), + ); + + final lineChartPainter = LineChartPainter(); + + final holder = + PaintHolder(data, data, TextScaler.noScaling); + final mockCanvasWrapper = MockCanvasWrapper(); + when(mockCanvasWrapper.size).thenAnswer((realInvocation) => viewSize); + when(mockCanvasWrapper.canvas).thenReturn(MockCanvas()); + + final mockBuildContext = MockBuildContext(); + + final results = >[]; + when( + mockCanvasWrapper.drawRect( + captureAny, + captureAny, + ), + ).thenAnswer((inv) { + results.add({ + 'rect': inv.positionalArguments[0] as Rect?, + 'paint': inv.positionalArguments[1] as Paint?, + }); + }); + + lineChartPainter.drawExtraLines( + mockBuildContext, + mockCanvasWrapper, + holder, + ); + + expect(results.length, 1); + + final rect = results[0]['rect'] as Rect; + + const expected = Rect.fromLTRB(54.5, 90, 96.5, 104); + expect( + HelperMethods.equalsRects( + rect, + expected, + ), + true, + reason: 'expected $rect to equal $expected', + ); + }); + + test('horizontalOffset should move vertical line label - 7', () { + const viewSize = Size(100, 100); + + final data = LineChartData( + minY: -1, + maxY: 10, + minX: -1, + maxX: 10, + titlesData: const FlTitlesData(show: false), + extraLinesData: ExtraLinesData( + verticalLines: [ + VerticalLine( + x: 5, + color: Colors.white, + label: VerticalLineLabel( + horizontalOffset: 10, + show: true, + style: const TextStyle( + color: Colors.white, + fontSize: 10, + ), + ), + ), + ], + ), + ); + + final lineChartPainter = LineChartPainter(); + + final holder = + PaintHolder(data, data, TextScaler.noScaling); + final mockCanvasWrapper = MockCanvasWrapper(); + when(mockCanvasWrapper.size).thenAnswer((realInvocation) => viewSize); + when(mockCanvasWrapper.canvas).thenReturn(MockCanvas()); + + final mockBuildContext = MockBuildContext(); + + final results = >[]; + when( + mockCanvasWrapper.drawRect( + captureAny, + captureAny, + ), + ).thenAnswer((inv) { + results.add({ + 'rect': inv.positionalArguments[0] as Rect?, + 'paint': inv.positionalArguments[1] as Paint?, + }); + }); + + lineChartPainter.drawExtraLines( + mockBuildContext, + mockCanvasWrapper, + holder, + ); + + expect(results.length, 1); + + final rect = results[0]['rect'] as Rect; + + const expected = Rect.fromLTRB(64.5, 100, 106.5, 114); + expect( + HelperMethods.equalsRects( + rect, + expected, + ), + true, + reason: 'expected $rect to equal $expected', + ); + }); + + test('horizontalOffset should move vertical line label - 8', () { + const viewSize = Size(100, 100); + + final data = LineChartData( + minY: -1, + maxY: 10, + minX: -1, + maxX: 10, + titlesData: const FlTitlesData(show: false), + extraLinesData: ExtraLinesData( + verticalLines: [ + VerticalLine( + x: 5, + color: Colors.white, + label: VerticalLineLabel( + horizontalOffset: -10, + show: true, + style: const TextStyle( + color: Colors.white, + fontSize: 10, + ), + ), + ), + ], + ), + ); + + final lineChartPainter = LineChartPainter(); + + final holder = + PaintHolder(data, data, TextScaler.noScaling); + final mockCanvasWrapper = MockCanvasWrapper(); + when(mockCanvasWrapper.size).thenAnswer((realInvocation) => viewSize); + when(mockCanvasWrapper.canvas).thenReturn(MockCanvas()); + + final mockBuildContext = MockBuildContext(); + + final results = >[]; + when( + mockCanvasWrapper.drawRect( + captureAny, + captureAny, + ), + ).thenAnswer((inv) { + results.add({ + 'rect': inv.positionalArguments[0] as Rect?, + 'paint': inv.positionalArguments[1] as Paint?, + }); + }); + + lineChartPainter.drawExtraLines( + mockBuildContext, + mockCanvasWrapper, + holder, + ); + + expect(results.length, 1); + + final rect = results[0]['rect'] as Rect; + + const expected = Rect.fromLTRB(44.5, 100, 86.5, 114); + expect( + HelperMethods.equalsRects( + rect, + expected, + ), + true, + reason: 'expected $rect to equal $expected', + ); + }); + + test('vertical line label padding should apply badding - 9', () { + const viewSize = Size(100, 100); + + final data = LineChartData( + minY: -1, + maxY: 10, + minX: -1, + maxX: 10, + titlesData: const FlTitlesData(show: false), + extraLinesData: ExtraLinesData( + verticalLines: [ + VerticalLine( + x: 5, + color: Colors.white, + label: VerticalLineLabel( + show: true, + padding: const EdgeInsets.all(16), + style: const TextStyle( + color: Colors.white, + fontSize: 10, + ), + ), + ), + ], + ), + ); + + final lineChartPainter = LineChartPainter(); + + final holder = + PaintHolder(data, data, TextScaler.noScaling); + final mockCanvasWrapper = MockCanvasWrapper(); + when(mockCanvasWrapper.size).thenAnswer((realInvocation) => viewSize); + when(mockCanvasWrapper.canvas).thenReturn(MockCanvas()); + + final mockBuildContext = MockBuildContext(); + + final results = >[]; + when( + mockCanvasWrapper.drawRect( + captureAny, + captureAny, + ), + ).thenAnswer((inv) { + results.add({ + 'rect': inv.positionalArguments[0] as Rect?, + 'paint': inv.positionalArguments[1] as Paint?, + }); + }); + + lineChartPainter.drawExtraLines( + mockBuildContext, + mockCanvasWrapper, + holder, + ); + + expect(results.length, 1); + + final rect = results[0]['rect'] as Rect; + + const expected = Rect.fromLTRB(38.5, 84, 112.5, 130); + expect( + HelperMethods.equalsRects( + rect, + expected, + ), + true, + reason: 'expected $rect to equal $expected', + ); + }); + + test('horizontal line label padding should apply badding - 10', () { + const viewSize = Size(100, 100); + + final data = LineChartData( + minY: -1, + maxY: 10, + minX: -1, + maxX: 10, + titlesData: const FlTitlesData(show: false), + extraLinesData: ExtraLinesData( + horizontalLines: [ + HorizontalLine( + y: 5, + color: Colors.white, + label: HorizontalLineLabel( + show: true, + padding: const EdgeInsets.all(16), + style: const TextStyle( + color: Colors.white, + fontSize: 10, + ), + ), + ), + ], + ), + ); + + final lineChartPainter = LineChartPainter(); + + final holder = + PaintHolder(data, data, TextScaler.noScaling); + final mockCanvasWrapper = MockCanvasWrapper(); + when(mockCanvasWrapper.size).thenAnswer((realInvocation) => viewSize); + when(mockCanvasWrapper.canvas).thenReturn(MockCanvas()); + + final mockBuildContext = MockBuildContext(); + + final results = >[]; + when( + mockCanvasWrapper.drawRect( + captureAny, + captureAny, + ), + ).thenAnswer((inv) { + results.add({ + 'rect': inv.positionalArguments[0] as Rect?, + 'paint': inv.positionalArguments[1] as Paint?, + }); + }); + + lineChartPainter.drawExtraLines( + mockBuildContext, + mockCanvasWrapper, + holder, + ); + + expect(results.length, 1); + + final rect = results[0]['rect'] as Rect; + + const expected = Rect.fromLTRB(-16, 15.5, 58, 61.5); + expect( + HelperMethods.equalsRects( + rect, + expected, + ), + true, + reason: 'expected $rect to equal $expected', + ); }); }); From 8468897d61ca1e224025a12e07b2a3075f94e1e3 Mon Sep 17 00:00:00 2001 From: Jani Koponen Date: Sun, 3 Mar 2024 20:09:12 +0200 Subject: [PATCH 25/27] Fix comments --- lib/src/chart/base/axis_chart/axis_chart_data.dart | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/lib/src/chart/base/axis_chart/axis_chart_data.dart b/lib/src/chart/base/axis_chart/axis_chart_data.dart index 483994c0a..1da97f065 100644 --- a/lib/src/chart/base/axis_chart/axis_chart_data.dart +++ b/lib/src/chart/base/axis_chart/axis_chart_data.dart @@ -1116,11 +1116,11 @@ class VerticalLine extends FlLine with EquatableMixin { /// Draws a title on the [HorizontalLine] class HorizontalLineLabel extends FlLineLabel with EquatableMixin { /// Draws a title on the [HorizontalLine], align it with [alignment] over the line, - /// applies [padding] for label padding, applies [margin] for label space andapplies [style] for changing color, + /// applies [padding] for label padding, applies [verticalOffset] and [horizontalOffset] for label space and applies [style] for changing color, /// size, ... of the text. /// Drawing text will retrieve through [labelResolver], /// you can override it with your custom data. - /// /// [show] determines showing label or not. + /// [show] determines showing label or not. HorizontalLineLabel({ EdgeInsets? padding, double? horizontalOffset, @@ -1179,7 +1179,7 @@ class HorizontalLineLabel extends FlLineLabel with EquatableMixin { /// Draws a title on the [VerticalLine] class VerticalLineLabel extends FlLineLabel with EquatableMixin { /// Draws a title on the [VerticalLine], align it with [alignment] over the line, - /// applies [padding] for label padding, [style] for changing color, + /// applies [padding] for label padding, applies [verticalOffset] and [horizontalOffset] for label space and applies [style] for changing color, /// size, ... of the text. /// Drawing text will retrieve through [labelResolver], /// you can override it with your custom data. From 60fc36a3a02ece92b493cf8655d2028c0c366eb2 Mon Sep 17 00:00:00 2001 From: Jani Koponen Date: Sun, 3 Mar 2024 20:17:06 +0200 Subject: [PATCH 26/27] Update changelog and documentation --- CHANGELOG.md | 3 ++- lib/src/chart/line_chart/line_chart_data.dart | 2 +- repo_files/documentations/scatter_chart.md | 2 +- 3 files changed, 4 insertions(+), 3 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index be9da14f6..8fa545281 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,6 +2,7 @@ * **IMPROVEMENT** (by @k0psutin) Add `tooltipPadding` to BarTouchTooltipData, LineTouchTooltipData and ScatterTouchTooltipData, #824 * **BREAKING** (by @k0psutin) Remove `margin` from HorizontalLineLabel and VerticalLineLabel, #824 +* **BREAKING** (by @k0psutin) Remove `bottomMargin` from ScatterTooltipItem , #824 * **IMPROVEMENT** (by @k0psutin) Add `verticalOFfset` and `horizontalOffset` to HorizontalLineLabel and VerticalLineLabel to replace `margin`, #824 * **BREAKING** (by @k0psutin) Remove `tooltipMargin` from HorizontalLineLabel and VerticalLineLabel, #824 * **BREAKING** (by @kopsutin) Add property `tooltipVerticalOffset` to BarTouchTooltipData, LineTouchTooltipData and ScatterTooltipItem to replace `tooltipMargin`, #824 @@ -26,7 +27,7 @@ BarTouchTooltipData( /// Migration guide: /// Old way: ScatterTooltipItem( - tooltipMargin: 10, + bottomMargin: 10, ) /// New way: diff --git a/lib/src/chart/line_chart/line_chart_data.dart b/lib/src/chart/line_chart/line_chart_data.dart index 6d03184e6..9a32359b1 100644 --- a/lib/src/chart/line_chart/line_chart_data.dart +++ b/lib/src/chart/line_chart/line_chart_data.dart @@ -805,7 +805,7 @@ bool showAllDots(FlSpot spot, LineChartBarData barData) { /// Shows a text label abstract class FlLineLabel with EquatableMixin { /// Draws a title on the line, align it with [alignment] over the line, - /// applies [padding] for label padding, applies [margin] for label space andapplies [style] for changing color, + /// applies [padding] for label padding, applies [horizontalOffset] and [verticalOffset] for label space andapplies [style] for changing color, /// size, ... of the text. /// [show] determines showing label or not. const FlLineLabel({ diff --git a/repo_files/documentations/scatter_chart.md b/repo_files/documentations/scatter_chart.md index 084ee49ff..f00b9dc79 100644 --- a/repo_files/documentations/scatter_chart.md +++ b/repo_files/documentations/scatter_chart.md @@ -55,6 +55,7 @@ When you change the chart's state, it animates to the new state internally (usin |tooltipPadding|padding of the tooltip|EdgeInsets.symmetric(horizontal: 16, vertical: 8)| |tooltipHorizontalAlignment|horizontal alginment of tooltip relative to the spot|FLHorizontalAlignment.center| |tooltipHorizontalOffset|horizontal offset of tooltip|0| +|tooltipVerticalOffset|vertical offset of tooltip|0| |maxContentWidth|maximum width of the tooltip (if a text row is wider than this, then the text breaks to a new line|120| |getTooltipItems|a callback that retrieve a [ScatterTooltipItem](#ScatterTooltipItem) by the given [ScatterSpot](#ScatterSpot) |defaultScatterTooltipItem| |fitInsideHorizontally| forces tooltip to horizontally shift inside the chart's bounding box| false| @@ -66,7 +67,6 @@ When you change the chart's state, it animates to the new state internally (usin |text|text string of each row in the tooltip bubble|null| |textStyle|[TextStyle](https://api.flutter.dev/flutter/dart-ui/TextStyle-class.html) of the showing text row|null| |textDirection|[TextDirection](https://api.flutter.dev/flutter/dart-ui/TextDirection-class.html) of the showing text row|TextDirection.ltr| -|bottomMargin| bottom margin of the tooltip (to the top of most top spot) | 0| |children|[List](https://api.flutter.dev/flutter/painting/InlineSpan-class.html) pass additional InlineSpan children for a more advance tooltip|null| From 78e9b8049237c7090106d64e6af120df8b1cd73b Mon Sep 17 00:00:00 2001 From: Jani Koponen Date: Sun, 3 Mar 2024 20:21:06 +0200 Subject: [PATCH 27/27] Remove visible for testing --- lib/src/chart/base/axis_chart/axis_chart_painter.dart | 3 --- 1 file changed, 3 deletions(-) diff --git a/lib/src/chart/base/axis_chart/axis_chart_painter.dart b/lib/src/chart/base/axis_chart/axis_chart_painter.dart index 219971620..ce05ced13 100644 --- a/lib/src/chart/base/axis_chart/axis_chart_painter.dart +++ b/lib/src/chart/base/axis_chart/axis_chart_painter.dart @@ -215,7 +215,6 @@ abstract class AxisChartPainter } } - @visibleForTesting void drawExtraLines( BuildContext context, CanvasWrapper canvasWrapper, @@ -234,7 +233,6 @@ abstract class AxisChartPainter } } - @visibleForTesting void drawHorizontalLines( BuildContext context, CanvasWrapper canvasWrapper, @@ -340,7 +338,6 @@ abstract class AxisChartPainter } } - @visibleForTesting void drawVerticalLines( BuildContext context, CanvasWrapper canvasWrapper,