背景:用户需要时间输入控件,尤其是小时、分钟,而flex自带的日期控件并无时、分、秒输入控件,于是做了一个日期时间自定义控件。
思路:
1)使用6个文本输入框、5个文本显示框(-,:等显示)和一个数字微调器;
2)开放selectedDate属性,用于设置初始时间和返回时间;
3)捕捉文本框的focusin事件,告诉数字微调器,需要微调年还是微调月或者日等;
4)捕捉文本框的foucsout事件,判断用户输入的年、月、日、时、分和秒是否合法。
下述为mxml代码
<?xml version="1.0" encoding="utf-8"?> <mx:HBox xmlns:fx="http://ns.adobe.com/mxml/2009" xmlns:s="library://ns.adobe.com/flex/spark" xmlns:mx="library://ns.adobe.com/flex/mx" width="144" horizontalGap="0" height="23" creationComplete="init()" paddingLeft="0" paddingRight="0" paddingBottom="0" paddingTop="0" borderStyle="solid"> <fx:Script> <![CDATA[ private var _now:Date = new Date(); [Bindable]private var iyear:int = _now.fullYear; [Bindable]private var imonth:int = _now.month+1; [Bindable]private var iday:int = _now.date; [Bindable]private var ihour:int = _now.hours; [Bindable]private var iminiute:int = _now.minutes; [Bindable]private var isecond:int = _now.seconds;
private function init():void{ the_button.textDisplay.width = 0; the_button.textDisplay.editable = false; the_button.textDisplay.setStyle("borderVisible","false"); the_button.textDisplay.setStyle("borderStyle","none"); }
private var _textInput:TextInput = the_year;
public function get selectedDate():Date{ return new Date(iyear,imonth-1,iday,ihour,iminiute,isecond); }
public function set selectedDate(value:Date):void{ if(value!=null){ iyear = value.fullYear; imonth = value.month+1; iday = value.date; ihour = value.hours; iminiute = value.minutes; isecond = value.seconds; } }
protected function the_year_focusInHandler(event:FocusEvent):void { _textInput = the_year; }
protected function the_month_focusInHandler(event:FocusEvent):void { _textInput = the_month; }
protected function the_day_focusInHandler(event:FocusEvent):void { _textInput = the_day; }
protected function the_hour_focusInHandler(event:FocusEvent):void { _textInput = the_hour; }
protected function the_miniute_focusInHandler(event:FocusEvent):void { _textInput = the_miniute; }
protected function the_second_focusInHandler(event:FocusEvent):void { _textInput = the_second; }
/** * format number's output */ private function formatNumberWithChar(value:Number,digit:Number,alpha:String):String{ var src:String = String(value); if(src.length>=digit){ return src; }else{ var len:int = digit - src.length; var temp:String = ""; for(var i:int = 0; i<len; i++){ temp+=alpha; } return alpha+src; } }
protected function the_button_clickHandler(event:MouseEvent):void { if(event.target == the_button.incrementButton){ if(_textInput == the_year){ //year part iyear +=1; }else if(_textInput==the_month){ //month part imonth+=1; if(imonth>12) imonth = 1; }else if(_textInput==the_day){ iday+=1; if(iday>getMonthDays(iyear,imonth)) iday = 1; }else if(_textInput==the_hour){ ihour+=1; if(ihour>23) ihour = 0; }else if(_textInput==the_miniute){ iminiute+=1; if(iminiute>59) iminiute=0; }else if(_textInput == the_second){ isecond+=1; if(isecond>59) isecond = 0; } }else if(event.target==the_button.decrementButton){ if(_textInput == the_year){ if(iyear>1970) iyear -=1; }else if(_textInput==the_month){ //month part imonth -= 1; if(imonth<1) imonth=12; }else if(_textInput==the_day){ iday -= 1; if(iday<1) iday = getMonthDays(iyear,imonth); }else if(_textInput==the_hour){ ihour -= 1; if(ihour<0)ihour = 23; }else if(_textInput==the_miniute){; iminiute-=1; if(iminiute<0)iminiute = 59; }else if(_textInput == the_second){ isecond -= 1; if(isecond<0) isecond =59; } } }
protected function the_second_focusOutHandler(event:FocusEvent):void { isecond = int(the_second.text); if(isecond>59) isecond = 0; }
protected function the_miniute_focusOutHandler(event:FocusEvent):void { iminiute = int(the_miniute.text); if(iminiute>59) iminiute = 0; }
protected function the_hour_focusOutHandler(event:FocusEvent):void { ihour = int(the_hour.text); if(ihour>23) ihour = 0; }
protected function the_day_focusOutHandler(event:FocusEvent):void { iday = int(the_day.text); if(iday>getMonthDays(iyear,imonth)) iday = 1; }
protected function the_month_focusOutHandler(event:FocusEvent):void { imonth = int(the_month.text); if(imonth>12) imonth = 1; }
protected function the_year_focusOutHandler(event:FocusEvent):void { iyear = int(the_year.text); if(iyear<1970) iyear = 1970; }
private function isLeapYear(year:int):Boolean{ if(year%4==0 && year %100!=0 || year %400==0) return true; else return false; } // private function getMonthDays(year:int, month:int):int{ var days:int = 0; switch(month){ case 1: case 3: case 5: case 7: case 8: case 10: case 12: days = 31; break; case 4: case 6: case 9: case 11: days = 30; break; case 2: days = (isLeapYear(year))?29:28; break; } return days; } ]]> </fx:Script> <s:TextInput id="the_year" restrict="0-9" maxChars="4" width="32" borderVisible="false" text="{iyear}" textAlign="right" focusIn="the_year_focusInHandler(event)" paddingRight="0" focusOut="the_year_focusOutHandler(event)"/> <s:TextInput text="-" editable="false" borderVisible="false" width="5" paddingLeft="0" paddingRight="0"/> <s:TextInput id="the_month" restrict="0-9" maxChars="2" width="16" borderVisible="false" text="{formatNumberWithChar(imonth,2,'0')}" textAlign="right" focusIn="the_month_focusInHandler(event)" paddingRight="0" focusOut="the_month_focusOutHandler(event)"/> <s:TextInput text="-" editable="false" borderVisible="false" width="5" paddingLeft="0" paddingRight="0"/> <s:TextInput id="the_day" restrict="0-9" maxChars="2" width="16" borderVisible="false" text="{formatNumberWithChar(iday,2,'0')}" textAlign="right" focusIn="the_day_focusInHandler(event)" paddingRight="0" focusOut="the_day_focusOutHandler(event)"/> <s:TextInput text="" editable="false" borderVisible="false" width="5" paddingLeft="0" paddingRight="0"/> <s:TextInput id="the_hour" restrict="0-9" maxChars="2" width="16" borderVisible="false" text="{formatNumberWithChar(ihour,2,'0')}" textAlign="right" focusIn="the_hour_focusInHandler(event)" paddingRight="0" focusOut="the_hour_focusOutHandler(event)"/> <s:TextInput text=":" editable="false" borderVisible="false" width="5" paddingLeft="0" paddingRight="0"/> <s:TextInput id="the_miniute" restrict="0-9" maxChars="2" width="16" borderVisible="false" text="{formatNumberWithChar(iminiute,2,'0')}" textAlign="right" focusIn="the_miniute_focusInHandler(event)" paddingRight="0" focusOut="the_miniute_focusOutHandler(event)"/> <s:TextInput text=":" editable="false" borderVisible="false" width="5" paddingLeft="0" paddingRight="0"/> <s:TextInput id="the_second" restrict="0-9" maxChars="2" width="16" borderVisible="false" text="{formatNumberWithChar(isecond,2,'0')}" textAlign="right" focusIn="the_second_focusInHandler(event)" focusOut="the_second_focusOutHandler(event)"/> <s:NumericStepper id="the_button" width="18" borderVisible="false" click="the_button_clickHandler(event)"/> </mx:HBox> |
应用演示:创建一个mxml Application,如下:
<?xml version="1.0" encoding="utf-8"?> <s:Application xmlns:fx="http://ns.adobe.com/mxml/2009" xmlns:s="library://ns.adobe.com/flex/spark" xmlns:mx="library://ns.adobe.com/flex/mx" width="523" height="306" xmlns:controls="whh.flex.controls.*" fontSize="12" xmlns:local="*"> <s:layout> <s:BasicLayout/> </s:layout>
<fx:Script> <![CDATA[ import mx.controls.Alert; protected function btnShowDateTime_clickHandler(event:MouseEvent):void { Alert.show(dateTime.selectedDate.toLocaleString()); } ]]> </fx:Script>
<fx:Script> <![CDATA[ private var aa:DateTimeField; ]]> </fx:Script>
<s:Panel id="panel" title="日期时间输入控件演示" width="429"> <local:DateTimeField id="dateTime" selectedDate="{new Date()}" width="161" x="0" y="5"/> <s:Button id="btnShowDateTime" label = "显示时间" click="btnShowDateTime_clickHandler(event)" x="164" y="6"/> </s:Panel> </s:Application> |