前言
各位同學大家好 有段時間沒有給大家更新文章了,具體多久我也記不清楚了 ,最近寫了一個flutter時間選擇的demo 就想着分享給大家 那么廢話不多說我們正式開始
准備工作
需要安裝flutter的開發環境:大家可以去看看之前的教程:
1 win系統flutter開發環境安裝教程: https://www.jianshu.com/p/152447bc8718
2 mac系統flutter開發環境安裝教程:https://www.jianshu.com/p/bad2c35b41e3
效果圖:
需要用到三方庫
flutter_picker: 1.1.5
# 彈框 https://pub.dev/packages/fluttertoast#-installing-tab-
fluttertoast: ^7.0.4
# 時間格式轉換 https://pub.dev/packages/date_format
date_format: 1.0.8
請在pubspec.yaml 文件中添加依賴 然后在控制台輸入flutter pub get 下載依賴
具體代碼實現:
單例
static void showStringPicker<T>(
BuildContext context, {
@required List<T> data,
String title,
int normalIndex,
PickerDataAdapter adapter,
@required _StringClickCallBack clickCallBack,
}) {
openModalPicker(context,
adapter: adapter ?? PickerDataAdapter( pickerdata: data, isArray: false),
clickCallBack:(Picker picker, List<int> selecteds){
// print(picker.adapter.text);
clickCallBack(selecteds[0],data[selecteds[0]]);
},
selecteds: [normalIndex??0] ,
title: title);
}
static void openModalPicker(
BuildContext context, {
@required PickerAdapter adapter,
String title,
List<int> selecteds,
@required PickerConfirmCallback clickCallBack,
}) {
new Picker(
adapter: adapter,
title: new Text(title ?? "請選擇",style:TextStyle(color: _kTitleColor,fontSize: _kTextFontSize)),
selecteds: selecteds,
cancelText: '取消',
confirmText: '確定',
cancelTextStyle: TextStyle(color: _kBtnColor,fontSize: _kTextFontSize),
confirmTextStyle: TextStyle(color: _kBtnColor,fontSize: _kTextFontSize),
textAlign: TextAlign.right,
itemExtent: _kItemHeight,
height: _kPickerHeight,
selectedTextStyle: TextStyle(color: Colors.black),
onConfirm:clickCallBack
).showModal(context);
}
我們定義了一個 靜態方法 showStringPicker () 需要傳入上下文 context 顯示列表數據 @required List
具體外部調用
單列
JhPickerTool.showStringPicker(context,
data: aa,
normalIndex: 2,
// title: "請選擇2",
clickCallBack: (int index,var str){
print(index);
print(str);
showText(str);
}
);
多列
JhPickerTool.showArrayPicker(context,
data: bb,
title: "請選擇2",
normalIndex: [0,1,0],
clickCallBack:(var index, var strData){
print(index);
print(strData);
showText(strData);
}
);
時間選擇器:
具體實現:
static void showDatePicker(
BuildContext context, {
DateType dateType,
String title,
DateTime maxValue,
DateTime minValue,
DateTime value,
DateTimePickerAdapter adapter,
@required _DateClickCallBack clickCallback,
}) {
int timeType;
if(dateType == DateType.YM){
timeType = PickerDateTimeType.kYM;
}else if(dateType == DateType.YMD_HM){
timeType = PickerDateTimeType.kYMDHM;
}else if(dateType == DateType.YMD_AP_HM){
timeType = PickerDateTimeType.kYMD_AP_HM;
}else{
timeType = PickerDateTimeType.kYMD;
}
openModalPicker(context,
adapter: adapter ??
DateTimePickerAdapter(
type: timeType,
isNumberMonth: true,
yearSuffix: "年",
monthSuffix: "月",
daySuffix: "日",
strAMPM: const["上午", "下午"],
maxValue: maxValue ,
minValue: minValue,
value: value ?? DateTime.now(),
),
title: title,
clickCallBack:(Picker picker, List<int> selecteds){
var time = (picker.adapter as DateTimePickerAdapter).value;
var timeStr;
if(dateType == DateType.YM){
timeStr =time.year.toString()+"年"+time.month.toString()+"月";
}else if(dateType == DateType.YMD_HM){
timeStr =time.year.toString()+"年"+time.month.toString()+"月"+time.day.toString()+"日"+time.hour.toString()+"時"+time.minute.toString()+"分";
}else if(dateType == DateType.YMD_AP_HM){
var str = formatDate(time, [am])=="AM" ? "上午":"下午";
timeStr =time.year.toString()+"年"+time.month.toString()+"月"+time.day.toString()+"日"+str+time.hour.toString()+"時"+time.minute.toString()+"分";
}else{
timeStr =time.year.toString()+"年"+time.month.toString()+"月"+time.day.toString()+"日";
}
// print(formatDate(DateTime(1989, 02, 21), [yyyy, '-', mm, '-', dd]));
clickCallback(timeStr,picker.adapter.text);
}
);
}
這邊獲取時間選擇器 通過調用showDatePicker 方法
static void showDatePicker(
BuildContext context, {
DateType dateType,
String title,
DateTime maxValue,
DateTime minValue,
DateTime value,
DateTimePickerAdapter adapter,
@required _DateClickCallBack clickCallback,
})
我們這邊需要傳入 對應上下文 context 還有 時間選擇器類型 DateType 對應我們上圖的四種樣式
YM , YMD_HM ,YMD_AP_HM kYMD 這四種 還需傳入 最大時間和最小時間 DateTime maxValue, DateTime minValue, 這個非畢傳 看具體情況使用 ,以及我們的適配器
我們根據外部傳入的時間類型 我們把需要用到dataType 重新賦值
int timeType;
if(dateType == DateType.YM){
timeType = PickerDateTimeType.kYM;
}else if(dateType == DateType.YMD_HM){
timeType = PickerDateTimeType.kYMDHM;
}else if(dateType == DateType.YMD_AP_HM){
timeType = PickerDateTimeType.kYMD_AP_HM;
}else{
timeType = PickerDateTimeType.kYMD;
}
然后我們在showDatePicker 方法體里面調用 openModalPicker 我們封裝好底部彈窗選擇器的方法
openModalPicker(context,
adapter: adapter ??
DateTimePickerAdapter(
type: timeType,
isNumberMonth: true,
yearSuffix: "年",
monthSuffix: "月",
daySuffix: "日",
strAMPM: const["上午", "下午"],
maxValue: maxValue ,
minValue: minValue,
value: value ?? DateTime.now(),
),
title: title,
clickCallBack:(Picker picker, List<int> selecteds){
var time = (picker.adapter as DateTimePickerAdapter).value;
var timeStr;
if(dateType == DateType.YM){
timeStr =time.year.toString()+"年"+time.month.toString()+"月";
}else if(dateType == DateType.YMD_HM){
timeStr =time.year.toString()+"年"+time.month.toString()+"月"+time.day.toString()+"日"+time.hour.toString()+"時"+time.minute.toString()+"分";
}else if(dateType == DateType.YMD_AP_HM){
var str = formatDate(time, [am])=="AM" ? "上午":"下午";
timeStr =time.year.toString()+"年"+time.month.toString()+"月"+time.day.toString()+"日"+str+time.hour.toString()+"時"+time.minute.toString()+"分";
}else{
timeStr =time.year.toString()+"年"+time.month.toString()+"月"+time.day.toString()+"日";
}
// print(formatDate(DateTime(1989, 02, 21), [yyyy, '-', mm, '-', dd]));
clickCallback(timeStr,picker.adapter.text);
}
);
我們在 DateTimePickerAdapter 適配器總傳入我們從外部傳入的參數以及獲取到當前時間 DateTime.now(), 我們在 callback 回調方法中
通過picker.adapter 獲取到適配器里面的屬性value 拿到當前選擇的時間
var time = (picker.adapter as DateTimePickerAdapter).value;
具體轉化
clickCallBack:(Picker picker, List<int> selecteds){
var time = (picker.adapter as DateTimePickerAdapter).value;
var timeStr;
if(dateType == DateType.YM){
timeStr =time.year.toString()+"年"+time.month.toString()+"月";
}else if(dateType == DateType.YMD_HM){
timeStr =time.year.toString()+"年"+time.month.toString()+"月"+time.day.toString()+"日"+time.hour.toString()+"時"+time.minute.toString()+"分";
}else if(dateType == DateType.YMD_AP_HM){
var str = formatDate(time, [am])=="AM" ? "上午":"下午";
timeStr =time.year.toString()+"年"+time.month.toString()+"月"+time.day.toString()+"日"+str+time.hour.toString()+"時"+time.minute.toString()+"分";
}else{
timeStr =time.year.toString()+"年"+time.month.toString()+"月"+time.day.toString()+"日";
}
// print(formatDate(DateTime(1989, 02, 21), [yyyy, '-', mm, '-', dd]));
clickCallback(timeStr,picker.adapter.text);
}
然后進行格式化 年 月 日 這樣 返回給調用頁面
具體時間選擇器調用
if(str == "jhPickerTool-時間選擇YM"){
JhPickerTool.showDatePicker(
context,
dateType: DateType.YM,
clickCallback: (var str,var time){
print(str);
print(time);
showText(str);
}
);
}
if(str == "jhPickerTool-時間選擇YMD_HM"){
JhPickerTool.showDatePicker(
context,
dateType: DateType.YMD_HM,
clickCallback: (var str,var time){
print(str);
print(time);
showText(str);
}
);
}
if(str == "jhPickerTool-時間選擇YMD_AP_HM"){
JhPickerTool.showDatePicker(
context,
dateType: DateType.YMD_AP_HM,
clickCallback: (var str,var time){
print(str);
print(time);
showText(str);
}
);
}
}
到此我們時間選擇器和底部選擇器單列多列就算講完了
最后總結:
flutter里面提供比較好用的 flutter_picker: 1.1.5 date_format: 1.0.8 底部選擇器和 時間轉換的庫 供我們調用 所以底部彈窗的實現 這里也要感謝作者的共享 能讓我們開發變得簡單 有興趣的同學可以私研究用其他的方式可以實現也行我這里就不展開講了 , 最后希望我的文章能幫助到各位解決問題 ,以后我還會貢獻更多有用的代碼分享給大家。各位同學如果覺得文章還不錯 ,麻煩給關注和star,小弟在這里謝過啦!