背景關系:我將在我的應用程式中有幾個可滾動串列,并且我總是希望在添加專案時將它們滾動到最新專案。
問題:我的 ListView.builders 和添加專案的地方在我的小部件樹中相距甚遠。通過建構式傳遞所有這些滾動控制器似乎非常尷尬。
我的解決方案:當我目前正在使用 Provider 進行練習時,我想出了一個使用 Provider 的可行解決方案:
class ScrollControllerProvider with ChangeNotifier {
ScrollController _paneController = ScrollController();
//setting up all other controllers here later
get paneController {
return _paneController;
}
void scrollHistory() {
WidgetsBinding.instance?.addPostFrameCallback((_) {
if (_paneController.hasClients) {
_paneController.jumpTo(_paneController.position.maxScrollExtent);
}
});
}
}
我會將所有滾動控制器添加到該提供程式,并在我需要的地方獲取我需要的內容。它已經適用于其中之一,但 reddit 上的某個人告訴我這不是一個好主意,因為應該處置滾動控制器。我對生命周期的話題還不是很了解,并且很難對此進行評估。
問題:在這里使用 Provider 真的是個壞主意嗎?你能幫我理解為什么嗎?如果是,解決此問題的最佳方法是什么?
uj5u.com熱心網友回復:
Provider不是問題,在提供者內部使用一次性物品是。ScrollController是與其主要相關的一次性物品Widget,或者更好的說法是其State。
如果您想通知您的小部件有關新添加的專案,請在提供程式中創建一個變數并在您的小部件中偵聽該變數,然后使用您ScrollController來更改位置。
要了解有關您的問題的更多資訊,請查看ScrollController 類和Disposable 類
uj5u.com熱心網友回復:
對于后代,Payam Asefi 為我指明了正確的方向。
我現在怎么樣了。
tldr; Provider 包含一個可以切換的值和一個切換它的方法。我提供了我還可以訪問滾動控制器的值。如果它被切換,則使用滾動控制器。我提供了在向串列中添加新專案時切換值的方法。
添加專案 > 觸發提供程式中的值 > 偵聽器意識到值已更改呼叫構建方法 > 滾動控制器用于轉到 maxscrollextend。
帶代碼的長答案:
提供者 a) 可以切換的布林值 b) 切換布林值的方法 c) 布林值的 getter
代碼:
class ScrollControllerToggles with ChangeNotifier {
bool _historyPaneSwitch = true;
get getTogglePaneSwitch {
return _historyPaneSwitch;
}
void toggleHistoryPane() {
_historyPaneSwitch = !_historyPaneSwitch;
notifyListeners();
}
}
在小部件中,我使用 Listview.builder:a) 我定義了一個滾動控制器,b) 我使用了一個依賴于該 Provider 內的 _historyPaneSwitch 的函式。該函式還使用滾動控制器將串列滾動到末尾。
void triggerScrollController() {
bool scrollHistoryPane =
Provider.of<ScrollControllerToggles>(context).getTogglePaneSwitch;
WidgetsBinding.instance?.addPostFrameCallback((_) {
if (paneController.hasClients) {
paneController.jumpTo(paneController.position.maxScrollExtent);
}
});
}
在向串列添加新專案的小部件中,我再次訪問提供程式并獲取切換“_historyPaneSwitch”的方法。
Function scrollHistoryPane =
Provider.of<ScrollControllerToggles>(context).toggleHistoryPane;
void dayChange(Function scrollHistoryPane) {
mainElementList.insert(0, MainElement(false, DateTime.now().toString()));
scrollHistoryPane;
}
轉載請註明出處,本文鏈接:https://www.uj5u.com/net/425481.html
