簡介
一個電商APP窟社,商品詳情頁是很重要的頁面痊末。從需求情況來看唁盏,存在自己跳自己的情況内狸。同事說只要把preventDuplicates設置為false就可以了。
這該怎么理解升敲?
望文生義
網易詞典中參數(shù)名稱翻譯:
prevent Duplicates : 防止重復源碼中的參數(shù)注釋:
英文:
By default, GetX will prevent you from push a route that you already in,if you want to push anyway, set [preventDuplicates] to false
中文(網易翻譯):
默認情況下,GetX將阻止你推送一個你已經在的路由轰传,如果你想無論如何都要推送驴党,將[preventduplates]設置為false
看源碼
// var routeName = "/${page.runtimeType}";
routeName ??= "/${page.runtimeType}";
routeName = _cleanRouteName(routeName);
if (preventDuplicates && routeName == currentRoute) {
return null;
}
page: 一般只頁面,命名一般為xxxPage获茬,其實是一個Widget港庄,一般是一個類。
routeName和currentRoute是只路由恕曲,類型是String鹏氧。路由有專門的類,不過這里簡化為用一個字符串代表一個路由佩谣,也就是一個頁面把还。
routeName:其實就是類名前面加一個/。從代碼注釋來看茸俭,老版本只能是類名前面加個/吊履。新版本可以自定義,從外部傳入调鬓。
preventDuplicates默認值是true艇炎。所以當自己跳轉自己時,routeName == currentRoute將成立腾窝,直接返回null缀踪,啥也不做居砖。
所以,把preventDuplicates設置為false驴娃,就可以隨便跳了奏候。同事說得沒錯。
preventDuplicates的作用托慨,可以類比為“按鈕防抖”鼻由。 假設手一抖,“跳轉下一頁”按鈕點了多次厚棵,那么頁面只會加入一次蕉世,其他幾次“抖動點擊”相當于無效。
從源碼可以看出婆硬,當前的版本狠轻,自己跳自己也可以通過自己命名routeName的方式更加優(yōu)雅地實現(xiàn),不需要修改preventDuplicates彬犯,畢竟“防抖”還是有必要的向楼。
其實“防止重復”比參數(shù)注釋更加準確一點,已經在路由堆棧中的頁面還是可以加入的谐区,只要不是“抖動式”反復疊加就可以湖蜕。比如A跳B,B跳A宋列,A跳C昭抒,C跳A等等都是可以的。在堆棧中A頁面可以有多個炼杖。preventDuplicates只是防止腦殘式的A跳A
從這段簡短的代碼也可以看出灭返,關于“防抖”這點,Get的設計者還是花了點心思的坤邪。
toNamed方法
Future<T?>? toNamed<T>(
String page, {
dynamic arguments,
int? id,
bool preventDuplicates = true,
Map<String, String>? parameters,
}) {
if (preventDuplicates && page == currentRoute) {
return null;
}
if (parameters != null) {
final uri = Uri(path: page, queryParameters: parameters);
page = uri.toString();
}
return global(id).currentState?.pushNamed<T>(
page,
arguments: arguments,
);
}
從源碼上看熙含,Get.to和Get.toName是兩套完全不用方法,是對應Flutter原生push和pushNamed的膠水封裝艇纺。
在這里怎静,沒有routeName參數(shù),只能通過修改preventDuplicates為false來實現(xiàn)自己跳自己的目的黔衡。
通過Uri過渡消约,實現(xiàn)url后面拼接參數(shù)的實現(xiàn)方式也是可以借鑒一下的。
路由類型
- Dialog 類型是 GetDialogRoute员帮,繼承自 PopupRoute或粮。
- BottomSheet 類型是 GetModalBottomSheetRoute,繼承自 PopupRoute捞高。
- Snackbar 類型是 SnackRoute氯材,繼承自 OverlayRoute渣锦。
- Page 類型是GetPageRoute,繼承自 PageRoute氢哮。
出棧(入棧)類型限定
導致的問題
有些時候袋毙,在Dialog或者BottomSheet的基礎上,繼續(xù)調用Get.to或者Get.toNamed進行跳轉冗尤,由于PageRoute類型限制听盖,會導致currentRoute參數(shù)會和預想的有出入。現(xiàn)象就是有時候會出現(xiàn)點擊按鈕裂七,頁面打不開皆看。
解決方案
這個時候,currentRoute已經錯亂背零,要解決頁面無法打開腰吟,就應該把preventDuplicates設置為false
小結
綜合考慮Get.to和Get.toNamed的情況,再出現(xiàn)頁面無法打開的時候徙瓶,將preventDuplicates設置為false是最簡潔有效的解決方案毛雇。
當然,默認情況下侦镇,preventDuplicates就應該保持默認的true不動灵疮,“防抖”的功能在大多數(shù)情況下還是很有用的。
參考文章
【Flutter 問題系列第 67 篇】在 Flutter 中使用 Get 插件在 Dialog 彈窗中不能二次跳轉路由問題的解決方案