??????小菜繼續(xù)完善自定義 ACEPageMenu 滑動(dòng)菜單婿禽;主要處理基本的點(diǎn)擊事件以及在測(cè)試過程中遇到的小問題雀摘;
Offstage & Opacity
??????小菜在剛開始嘗試過程中遇到一個(gè)問題悠砚,當(dāng)只展示頂部和底部 Menu 時(shí)聘殖,Menu 中點(diǎn)擊事件無法觸發(fā)摄凡;分析之后發(fā)現(xiàn),小菜是在層級(jí) Stack 中存放四周 Menu,當(dāng)時(shí)采用 Offstage 使兩側(cè) Menu 不展示,但小菜忽略了一點(diǎn)技扼,Offstage 雖然是視覺不可見,但其子 Widget 依舊存在嫩痰,類似于 Android 的 android:visibility="invisible"剿吻;
??????之前小菜有總結(jié)過,采用 Offstage 可避免不展示的內(nèi)容不進(jìn)行繪制串纺,調(diào)整之后便不會(huì)遮擋其他 Menu 的點(diǎn)擊事件丽旅;
switch (menuType) {
case MenuType.MENU_TOP:
_menuWid = Offstage(
offstage: _isShowTopMenu || _isShowMixMenu ? false : true,
child: _topMenuWid());
break;
case MenuType.MENU_BOTTOM:
_menuWid = Offstage(
offstage: _isShowBottomMenu || _isShowMixMenu ? false : true,
child: _bottomMenuWid());
break;
case MenuType.MENU_LEFT:
_menuWid = Offstage(
offstage: _isShowLeftMenu ? false : true, child: _leftMenuWid());
break;
case MenuType.MENU_RIGHT:
_menuWid = Offstage(
offstage: _isShowRightMenu ? false : true, child: _rightMenuWid());
break;
}
typedef
??????小菜在自定義滑動(dòng)菜單時(shí)椰棘,會(huì)有很多類似的圖標(biāo)按鈕,為了代碼的簡(jiǎn)潔性榄笙,通過 typedef 提取公共的點(diǎn)擊事件邪狞;
typedef void OnMenuItemClicked(MenuItemType menuItemType, var operateData);
return GestureDetector(
child: Container(
height: MenuManager.topMenuIconSize,
width: MenuManager.topMenuIconSize,
child: Center(child: Icon(icon, color: Colors.white))),
onTap: () => menuItemClick(type, null));
??????typedef 小菜通常用作提取公共方法,可當(dāng)作希望指定特定功能匹配的功能簽名茅撞;借助 typedef帆卓,既可以將變量分配給函數(shù),也可以當(dāng)作函數(shù)參數(shù)米丘;
typedef void OnItemClicked(MenuItemType menuItemType, var operateData);
itemClick01(type, data) {
print('---itemClick01---type=$type---data=$data---');
}
itemClick02(type, data) {
print('---itemClick02---type=$type---data=$data---');
}
OnItemClicked itemClicked = itemClick01;
itemClicked(MenuItemType.MENU_CATALOG, 'Catalog!');
itemClicked = itemClick02;
itemClicked(MenuItemType.MENU_QZONE, 'QZone!');
ListView 頭部空白
??????小菜在嘗試左側(cè)滑動(dòng)菜單時(shí)剑令,添加了一個(gè) ListView 作為數(shù)據(jù)展示,但嘗試過程發(fā)現(xiàn) ListView 頂部會(huì)有一塊空白區(qū)域蠕蚜,而小菜并未設(shè)置 Header 或內(nèi)外邊距尚洽;查閱資料發(fā)現(xiàn),當(dāng) ListView 沒有與 AppBar 共同使用時(shí)靶累,MediaQuery 會(huì)默認(rèn)設(shè)置一個(gè) padding,通過 remove 去掉即可癣疟;
return MediaQuery.removePadding(
removeTop: true,
context: context,
child: Container(
child: ListView.builder(
itemCount: 100,
itemBuilder: (context, index) {
return Padding(
padding: EdgeInsets.only(left: 10.0, right: 10.0, top: 4.0, bottom: 4.0),
child: Row(children: <Widget>[
Expanded(child: Text('當(dāng)前 item = 當(dāng)前 item = 當(dāng)前 item =${index + 1}', style: TextStyle(fontSize: 16))),
Padding(child: Icon(Icons.lock_open, size: 14), padding: EdgeInsets.only(left: 10))
]));
})));
RawGestureDetector
??????小菜需要處理復(fù)雜的手勢(shì)操作挣柬,包括滑動(dòng)點(diǎn)擊等,單純的 GestureDetector 不足以完成睛挚,于是小菜嘗試用 RawGestureDetector 來處理手勢(shì)操作集合邪蛔;
class RawGestureDetector extends StatefulWidget {
const RawGestureDetector({
Key key,
this.child,
this.gestures = const <Type, GestureRecognizerFactory>{},
this.behavior,
this.excludeFromSemantics = false,
this.semantics,
})
}
??????RawGestureDetector 作為一個(gè)有狀態(tài)的 StatefulWidget 小部件,主要是處理 gestures 來攔截各種手勢(shì)操作扎狱;針對(duì)手勢(shì)這部分侧到,小菜會(huì)在今后的博客中詳細(xì)學(xué)習(xí),今天僅為實(shí)現(xiàn)基本的功能淤击;
??????小菜優(yōu)先實(shí)現(xiàn)基本的點(diǎn)擊事件匠抗,在攔截點(diǎn)擊時(shí),小菜通過 onUpdate 和 onEnd 配合處理污抬,當(dāng)沒有進(jìn)行滑動(dòng)汞贸,即手勢(shì)點(diǎn)擊的 Point 坐標(biāo)未改變時(shí),并且在 onEnd 方法中可攔截作為一次有效的點(diǎn)擊操作印机;
RawGestureDetector(
child: CustomPaint(painter: CommonLinePainter(context, 50.0)),
gestures: <Type, GestureRecognizerFactory>{
MenuGestureRecognizer:
GestureRecognizerFactoryWithHandlers<MenuGestureRecognizer>(
() => MenuGestureRecognizer(),
(MenuGestureRecognizer gesture) {
gesture.onDown = (detail) {
print('---MenuGestureRecognizer.onDown---$detail');
};
gesture.onUpdate = (detail) {
_isGestureSlide = true;
print('---MenuGestureRecognizer.onUpdate---$detail---${detail.localPosition}');
};
gesture.onEnd = (detail) {
if (!_isGestureSlide) {
_menuState(_isMenuShow ? MenuType.MENU_CLOSE : MenuType.MENU_MIX);
_isMenuShow = !_isMenuShow;
}
_isGestureSlide = false;
print('---MenuGestureRecognizer.onEnd---$detail---${detail.primaryVelocity}---${detail.velocity}---${detail.velocity.pixelsPerSecond}');
};
})
}))
??????ACEPageMenu 案例源碼
??????小菜對(duì)自定義 ACEPageMenu 的功能還不夠完善矢腻,會(huì)逐漸學(xué)習(xí)補(bǔ)充;如有錯(cuò)誤射赛,請(qǐng)多多指導(dǎo)多柑!
來源: 阿策小和尚