Flidter Linechart Widget не перестраивается при изменениях данных с провайдером с помощью уведомителя об изменениях - PullRequest
0 голосов
/ 03 апреля 2020

У меня в настоящее время есть экран с виджетом линейной диаграммы. Это виджет без состояния, использующий плагин Flchart.

источник данных для линейной диаграммы использует поставщика, который прослушивает изменения, у меня также есть фильтр даты. который вызывает API и получает данные для этого диапазона дат и обновляет данные

, что я нахожу, когда я обновляю sh данные для другого диапазона дат, я вижу, что данные отправляются в виджет, но линейный график не отображается / перестраивается, если я переключаюсь обратно на диапазон дат по умолчанию, первый загруженный график отображается правильно.

виджет линейного графика

class LineChartWidget extends StatelessWidget {
  final List<FlSpot> list;
  final bool isDollar;
  LineChartWidget({this.list, this.isDollar});

  final DateTime now = DateTime.now();
  double minY = 0;
  double maxY = 0;

  @override
  Widget build(BuildContext context) {
    list.forEach((f) => print(f.y.toString()));
    return list.isEmpty
        ? Container(
            child: Center(
              child: Text("No Chart Data..."),
            ),
          )
        : ConstrainedBox(
            constraints: BoxConstraints.expand(height: 140),
            child: LineChart(mainData()),
          );
  }

  static int dse2mse(double daysSinceEpoch) {
    return (daysSinceEpoch * 86400000).floor();
  }

  static double mse2dse(int millisecondsSinceEpoch) {
    return millisecondsSinceEpoch / 86400000;
  }

  String getTitleFunction(double value) {
    DateTime dateTime = DateTime.fromMillisecondsSinceEpoch(dse2mse(value));
    return DateFormat('MMM d').format(dateTime);
  }

  LineChartData mainData() {
    maxY = list[0].y;
    minY = list[0].y;
    list.forEach((i) {
      if (i.y < minY) {
        minY = i.y;
      }
      if (i.y > maxY) {
        maxY = i.y;
      }
    });

    return LineChartData(
      minX: mse2dse(DateTime(now.year, now.month, 1).millisecondsSinceEpoch),
      maxX: mse2dse(now.millisecondsSinceEpoch),
      minY: minY - 1.9 * minY,
      maxY: maxY + 0.2 * maxY,
      clipToBorder: true,
      gridData: FlGridData(
        show: false,
      ),
      titlesData: FlTitlesData(
        show: false,
      ),
      borderData: FlBorderData(
        show: false,
      ),
      lineTouchData: LineTouchData(
          fullHeightTouchLine: false,
          handleBuiltInTouches: true,
          getTouchedSpotIndicator:
              (LineChartBarData barData, List<int> spotIndexes) {
            return spotIndexes.map((spotIndex) {
              final FlSpot spot = barData.spots[spotIndex];
              if (spot.x == 0 || spot.x == 30 || spot.x == 29) {
                return null;
              }
              return TouchedSpotIndicatorData(
                const FlLine(color: Colors.transparent, strokeWidth: 0),
                const FlDotData(
                    dotSize: 5, dotColor: Color.fromRGBO(253, 54, 94, 1)),
              );
            }).toList();
          },
          touchTooltipData: LineTouchTooltipData(
              tooltipBgColor: Colors.white,
              fitInsideHorizontally: true,
              fitInsideVertically: true,
              getTooltipItems: (List<LineBarSpot> touchedBarSpots) {
                return touchedBarSpots.map((barSpot) {
                  final flSpot = barSpot;
                  if (flSpot.x == 0 || flSpot.x == 30 || flSpot.x == 29) {
                    return null;
                  }

                  return LineTooltipItem(
                    isDollar
                        ? '${getTitleFunction(flSpot.x)}  |  \$${flSpot.y}'
                        : '${getTitleFunction(flSpot.x)}  |  ${flSpot.y.toStringAsFixed(0)}',
                    const TextStyle(
                        color: Colors.black87,
                        fontFamily: 'NeueMontreal',
                        letterSpacing: 0.9,
                        fontWeight: FontWeight.w600,
                        fontSize: 12),
                  );
                }).toList();
              })),
      lineBarsData: [
        LineChartBarData(
          spots: list,
          isCurved: true,
          colors: [Color.fromRGBO(253, 54, 94, 1)],
          curveSmoothness: 0.17,
          barWidth: 1,
          isStrokeCapRound: true,
          dotData: const FlDotData(
            show: false,
          ),
        ),
      ],
    );
  }
}

я не уверен поможет ли изменение виджета линейной диаграммы на Stateful, так как я не могу вызвать setstate, потому что NotifyListers автоматически обновляет данные

спасибо

1 Ответ

0 голосов
/ 09 апреля 2020

Устранена проблема: линейный график не обновлялся, значения MinX и MaxX должны обновляться при изменении диапазона дат

...