본문 바로가기
flex- off

flex로 calender를 만들때, 해당하는 달의 날짜 구하기?

by 엉금둥이 2010. 5. 17.

 flex 에는 Date() 함수가 있습니다.

이 Date() 함수로 날짜, 시간들을 구할수가 있는데요 이것들을 간단하게 사용해 본다


var date:Date = new Date();   trace("출력 :::: " , date.getFullYear(), date.getMonth(), date.getDate());

===================================================================================
출력 :::: 2010 4 17
===================================================================================
이렇게 표현 된다는 것을 알 수 있습니다.

api를 보시면, 월은 0부터 시작해서 11까지, 0 - 1월이 되는 것이고 11은 12월이 되는... 이런 당연한 결과가 나오겠죠 ^^;

그렇다면, 원하는 달의 값을 받아서, 화면에 한번 뿌려주게되면


var date:Date = new Date();
    date.setFullYear(2010, 4, 1);  // 2010년 5월 1일로 셋팅해주고
    
    for(var i : int = 0 ; i < 40 ; i++)  // for문으로 40번을 셋팅
    {
     trace(date.getFullYear(), date.getMonth(), date.getDate());
     date.setDate(date.getDate() + 1);   // 매 회 마다 하루씩 늘려가기
    }
==================================================================================
2010 4 1
2010 4 2
2010 4 3
2010 4 4
---- 중략 ----
2010 4 29
2010 4 30
2010 4 31
2010 5 1
2010 5 2
2010 5 3
2010 5 4
2010 5 5
2010 5 6
2010 5 7
2010 5 8
2010 5 9
==================================================================================

이와같이 해당하는 달이 끝나면, 자동으로 다음달로 변경해주는^^ 계산을 내부적으로 해주고 있습니다

그렇다면... 왜 앞에서 내용을 이렇게 설명을 했느냐 하면..(전혀 매끄럽지 못한 내용)

요즘 달력의 모양은

아... 이미지를 어디서 찾아야 하나...
<출처, 네이버 캘린더>



해당하는 달의 일이 나오고, 나머지 빈 공간은, 전달과 다음달의 연장 달이 표시가 되는 형식이 많죠
이런 형식을 순차적으로  ArrayCollection 으로 받는 메소드를 만들어 보겠습니다.
여기에 하나 더 추가해서, 내가 원하는 요일을 맨 앞으로 넣었을 경우, 그 요일이 나오게끔 하는 옵션까지 넣는다 치고,
요일은 0은 일요일, 1은 월요일 ... 6은 토요일입니다

아래 소스를 보시죠 간단한 주석도 있습니다.
/**
    * 선택한 달
    * @param year 선택한 년
    * @param month 선택한 월 ===== 월 :: 0 - > 1월, 11 - > 12월
    * @param startDay 시작할 요일 , 범위는 0 ~ 6 ===== day :: 요일 0 - > 일요일, 6 - > 토요일
    */  
   public function selectMonth(year:int, month:int, startDay:int = 0):ArrayCollection
   {
    var date:Date = new Date(year, month);
    
    var AC:ArrayCollection = new ArrayCollection();
    
    var maxLen:int = 42;
    var i:int = 0;
    // 선택된 전달의 마지막 날짜
    var backLastDate:int = dateBackLastDate(year, month);
    // 선택한 전 달이 표시될 일자 수
    var backLimit:int = backAmbitDate(year, month, startDay);
    // 선택된 전달의 표시될 첫째 날짜
    var backStart:int = (backLastDate - backLimit) + 1;
    
    /* 현재 선택된 달의 전달을 구하는 for문 */
    var backYear:int = dateSetting(year, month, DATE_BACK).year;
    var backMonth:int = dateSetting(year, month, DATE_BACK).month;
    
    var backDate:Date = new Date(backYear, backMonth);
    
    for(i = backStart ; i <= backLastDate ; i++)
    {
     backDate.setDate(i);
     // 선택한 달의 첫 날이 인덱스의 맨 앞이면, 전달을 구할 필요가 없다 
     if(startDay == date.getDay())
     {
      break;
     }
     
     var backDataObj:Object = {year: backDate.getFullYear(), month: backDate.getMonth(), date: backDate.getDate()};
     
     AC.addItem(backDataObj);
    }
    
    /* 현재 선택된 달을 구하는 for문 */
    for(i = 1 ; i <= maxLen ; i++)
    {
     date.setDate(i);
     
     if(month != date.getMonth())
     {
      break;
     }
     
     var dataObj:Object = {year: date.getFullYear(), month: date.getMonth(), date: date.getDate()};
     
     AC.addItem(dataObj);
    }
    
    /* 현재 선택된 달의 다음달을 구하는 for문 */
    var nextYear:int = dateSetting(year, month, DATE_NEXT).year;
    var nextMonth:int = dateSetting(year, month, DATE_NEXT).month;
    
    var nextDate:Date = new Date(nextYear, nextMonth);
    
    for(i = 1 ; i < 7 ; i++)
    {
     nextDate.setDate(i);
     /* 선택한 달의 첫날의 인덱스와 다음달의 시작의 첫 날의 인덱스가 같다면, 다음달을 구할 필요가 없다*/
     
     if(startDay == nextDate.getDay())
     {
      break;
     }
     
     var nextDataObj:Object = {year: nextDate.getFullYear(), month: nextDate.getMonth(), date: nextDate.getDate()};
     
     AC.addItem(nextDataObj);
    }
    
    return AC;
   }

이놈에다가 필요한 정보를 넣게 되겠죠
그리고 이놈을 도와주는 메소드들은
/**
    * @param year 년
    * @param month 월
    * @return 선택된 달의 전달의 마지막 날짜
    */  
   public function dateBackLastDate(year:int, month:int):int
   {
    var date:Date = new Date(year, month);
    
    date.setDate(date.getDate() - 1);
    var lastDate:int = date.getDate();
    
    return lastDate;
   }
   
   /**
    * @param year 선택한 년도
    * @param month 선택한 월
    * @param mode 선택한 date에서, 전달 또는 다음달을 선택
    * @return 전달, 또는 다음달 년,월 :: obj
    */  
   private function dateSetting(year:int, month:int, mode:String):Object
   {
    if(mode == DATE_BACK)
    {
     month = month - 1;
     
     if(month < 0)
     {
      year = year - 1;
      month = 11;
     }
    }
    else if(mode == DATE_NEXT)
    {
     month = month + 1;
     if(month > 11)
     {
      year = year + 1;
      month = 0;
     }
    }
    
    var sObj:Object = {year: year, month: month};
    return sObj;
   }
   
   
   /**
    * @param date 선택된 달의 date
    * @param startDay 시작할 요일
    * @return 전달이 나와야 할 일자 수
    */  
   private function backAmbitDate(year:int, month:int, startDay:int = 0):int
   {
    var date:Date = new Date(year, month);
    
    var result:int;
    
    if(date.getDay() == startDay)
    {
     result = 0;
    }
    else
    {
     if(date.getDay() - startDay < 0)
     {
      result = 7 - (startDay - date.getDay());
     }
     else
     {
      result = date.getDay() - startDay;
     }
    }
    
    return result;
   }

이렇게 있습니다. 소스가 길고 좀... 정리가 안됐지만... 어쩌겠습니까... 저는 초보인걸. ㅠ_-

실행이 잘 되는지 돌려봐야겠죠??


내부적으로, 숫자 싱크를 맞춰서 데모를 올려봤어요

년 월 시작하는 요일을 입력하면, 순차적으로 데이타가 나올겁니다.

소스가 많이 지저분하지만... ~_~ 저처럼 초보 개발자?들을 위해~ 참고라도 되었으면 하네요