ShadyBoukhary / flutter_clean_architecture

Clean architecture flutter: A Flutter package that makes it easy and intuitive to implement Uncle Bob's Clean Architecture in Flutter. This package provides basic classes that are tuned to work with Flutter and are designed according to the Clean Architecture.

Home Page:https://pub.dartlang.org/packages/flutter_clean_architecture

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

refreshUI() doesn't work with Shared Controller.

stefanoBavest opened this issue · comments

Description

Firstly, thank you for this project. It's really useful in my project.
Coming to the issue, I am trying to implement a shared controller and presenter with multiple views.
Each view has its own controller and presenter as well.
I had referred to an earlier issue and the example provided as well:
#15

I have created a shared controller and presenter.
It is initialized in the widget tree above the other views and called further down in the tree where required.
The data is accessible and consumed by the widget.
However if I call refreshUI() in the shared controller to update data in the shared controller, the view does not get updated.

Code

Shared Controller
import 'package:flutter_clean_architecture/flutter_clean_architecture.dart';

class SharedController extends Controller {
  final BookmarkManager _bookmarkManager = BookmarkManager();
  final WatchlistManager _watchlistManager = WatchlistManager();

  List<dynamic>? _data = [];
  List<dynamic> _suggestions = [];
  
  Map<String, List<dynamic>> _overview = {};
  
  List<StockSuggestion> get suggestions => _suggestions;
  Map<String, List<StockData>> get overview => _overview;

  set overview(Map<String, List<StockData>> data) {
    _overview.addAll(data);
    refreshUI();
  }
  
  SharedController() : super();

  @override
  void initListeners() {
    _bookmarkManager.getBookMarkList().then((value) => _data = value);
    _watchlistManager.getWatchlists().then((value) => _watchlistTabs = value);
  }


  @mustCallSuper
  @override
  void onDisposed() {
    super.onDisposed();
  }

 updateSuggestions() async {
    /* API call for getting suggestions */
    var result = async ApiCallResult();
    /* Update suggestion */
    _suggestions = result;

   refreshUI();        <-- **Does not execute**
  }
}
Parent Widget
import 'package:example/app/pages/shared/shared_controller.dart';
import 'package:example/app/widgets/form/route_form.dart';
import 'package:flutter/material.dart';
import 'package:flutter_clean_architecture/flutter_clean_architecture.dart';

class RoutePage extends View {
  static _RouteState of(BuildContext context) =>
      context.findAncestorStateOfType<_RouteState>()!;

  @override
  _RouteState createState() => _RouteState();
}

class _RouteState extends ViewState<RoutePage, SharedController> {
  _RouteState() : super(SharedController());

  @override
  Widget get view {
    return ControlledWidgetBuilder<SharedController>(builder: (_, controller) {
      return RouteForm();
    });
  }
}

Child Widget
import 'package:example/app/pages/shared/shared_controller.dart';
import 'package:example/app/widgets/card/overview_card.dart';
import 'package:flutter/material.dart';
import 'package:flutter_clean_architecture/flutter_clean_architecture.dart';
import 'package:flutter_screenutil/flutter_screenutil.dart';

class OverviewSlider extends StatelessWidget {
  const OverviewSlider({Key? key}) : super(key: key);

  @override
  Widget build(BuildContext context) {
    return ControlledWidgetBuilder<SharedController>(
      builder: (_, controller) {
        return Container(
          height: 350.sp,
          child: Center(
            child: ListView.builder(
              scrollDirection: Axis.horizontal,
              itemBuilder: (_, index) {
                return OverviewCard(
                    controller: controller,
                    suggestion: controller.suggestions[index],
                    showCurrency: false);
              },
              itemCount: controller.suggestions.length,
            ),
          ),
        );
      },
    );
  }
}

On calling the updateSuggestions() method, the data is fetched and the _suggestions variable is updated.
However, the UI does not update.

Any help would be appreciated.

Library Version

  • flutter_clean_architecture: ^5.0.0

After referring to #68 I figured out the issue was related to different widgets using different instances of the shared controller.

My solution was initializing a single instance of the shared controller (static variable / singleton pattern) and using that throughout the widget tree.

I'm closing this issue as it has been resolved.