`
legend26
  • 浏览: 16733 次
  • 性别: Icon_minigender_1
  • 来自: 深圳
文章分类
社区版块
存档分类
最新评论

JS日历

阅读更多
JS日历,实现节假日和农历节气==
2011-06-28 16:00

2011.8.11修正bug 2个



JS 代码:

var lunarInfo=new Array(
0x04bd8,0x04ae0,0x0a570,0x054d5,0x0d260,0x0d950,0x16554,0x056a0,0x09ad0,0x055d2,
0x04ae0,0x0a5b6,0x0a4d0,0x0d250,0x1d255,0x0b540,0x0d6a0,0x0ada2,0x095b0,0x14977,
0x04970,0x0a4b0,0x0b4b5,0x06a50,0x06d40,0x1ab54,0x02b60,0x09570,0x052f2,0x04970,
0x06566,0x0d4a0,0x0ea50,0x06e95,0x05ad0,0x02b60,0x186e3,0x092e0,0x1c8d7,0x0c950,
0x0d4a0,0x1d8a6,0x0b550,0x056a0,0x1a5b4,0x025d0,0x092d0,0x0d2b2,0x0a950,0x0b557,
0x06ca0,0x0b550,0x15355,0x04da0,0x0a5d0,0x14573,0x052d0,0x0a9a8,0x0e950,0x06aa0,
0x0aea6,0x0ab50,0x04b60,0x0aae4,0x0a570,0x05260,0x0f263,0x0d950,0x05b57,0x056a0,
0x096d0,0x04dd5,0x04ad0,0x0a4d0,0x0d4d4,0x0d250,0x0d558,0x0b540,0x0b5a0,0x195a6,
0x095b0,0x049b0,0x0a974,0x0a4b0,0x0b27a,0x06a50,0x06d40,0x0af46,0x0ab60,0x09570,
0x04af5,0x04970,0x064b0,0x074a3,0x0ea50,0x06b58,0x055c0,0x0ab60,0x096d5,0x092e0,
0x0c960,0x0d954,0x0d4a0,0x0da50,0x07552,0x056a0,0x0abb7,0x025d0,0x092d0,0x0cab5,
0x0a950,0x0b4a0,0x0baa4,0x0ad50,0x055d9,0x04ba0,0x0a5b0,0x15176,0x052b0,0x0a930,
0x07954,0x06aa0,0x0ad50,0x05b52,0x04b60,0x0a6e6,0x0a4e0,0x0d260,0x0ea65,0x0d530,
0x05aa0,0x076a3,0x096d0,0x04bd7,0x04ad0,0x0a4d0,0x1d0b6,0x0d250,0x0d520,0x0dd45,
0x0b5a0,0x056d0,0x055b2,0x049b0,0x0a577,0x0a4b0,0x0aa50,0x1b255,0x06d20,0x0ada0)
var Animals=new Array("鼠","牛","虎","兔","龙","蛇","马","羊","猴","鸡","狗","猪");
var Gan=new Array("甲","乙","丙","丁","戊","己","庚","辛","壬","癸");
var Zhi=new Array("子","丑","寅","卯","辰","巳","午","未","申","酉","戌","亥");
var now;
var curDay;
var curMonth;
var curYear;
var maxd;
var maxDay;
var maxMonth;
var maxYear;
var tmpMonth;
var tmpMonth=curMonth;
var SY,SM,SD;
var startDate,startY,startM,startD,endDate,endY,endM,endD; // 关联日期的选取范围
var dateObj=null; //当前日期选择框

function cyclical(num) { return(Gan[num%10]+Zhi[num%12]) } //==== 传入 offset 传回干支, 0=甲子
//==== 传回农历 y年的总天数
function lYearDays(y) {
   var i, sum = 348
   for(i=0x8000; i>0x8; i>>=1) sum += (lunarInfo[y-1900] & i)? 1: 0
   return(sum+leapDays(y))
}

//==== 传回农历 y年闰月的天数
function leapDays(y) {
   if(leapMonth(y)) return((lunarInfo[y-1900] & 0x10000)? 30: 29)
   else return(0)
}

//==== 传回农历 y年闰哪个月 1-12 , 没闰传回 0
function leapMonth(y) { return(lunarInfo[y-1900] & 0xf)}

//====================================== 传回农历 y年m月的总天数
function monthDays(y,m) { return( (lunarInfo[y-1900] & (0x10000>>m))? 30: 29 )}

//==== 算出农历, 传入日期物件, 传回农历日期物件
//     该物件属性有 .year .month .day .isLeap .yearCyl .dayCyl .monCyl
function Lunar(objDate) {
   var i, leap=0, temp=0
   var baseDate = new Date(1900,0,31)
   var offset   = (objDate - baseDate)/86400000

   this.dayCyl = offset + 40
   this.monCyl = 14

   for(i=1900; i<2050 && offset>0; i++) {
      temp = lYearDays(i)
      offset -= temp
      this.monCyl += 12
   }
   if(offset<0) {
      offset += temp;
      i--;
      this.monCyl -= 12
   }

   this.year = i
   this.yearCyl = i-1864

   leap = leapMonth(i) //闰哪个月
   this.isLeap = false

   for(i=1; i<13 && offset>0; i++) {
      //闰月
      if(leap>0 && i==(leap+1) && this.isLeap==false)
         { --i; this.isLeap = true; temp = leapDays(this.year); }
      else
         { temp = monthDays(this.year, i); }

      //解除闰月
      if(this.isLeap==true && i==(leap+1)) this.isLeap = false

      offset -= temp
      if(this.isLeap == false) this.monCyl ++
   }

   if(offset==0 && leap>0 && i==leap+1)
      if(this.isLeap)
         { this.isLeap = false; }
      else
         { this.isLeap = true; --i; --this.monCyl;}

   if(offset<0){ offset += temp; --i; --this.monCyl; }

   this.month = i
   this.day = offset + 1
}

//==== 中文日期
function cDay(m,d){
    var nStr1 = new Array('日','一','二','三','四','五','六','七','八','九','十');
    var nStr2 = new Array('初','十','廿','卅',' ');
    var s;
    if (m>10){s = '十'+nStr1[m-10]} else {s = nStr1[m]} s += '月'
    switch (d) {
    case 10:s += '初十'; break;
    case 20:s += '二十'; break;
    case 30:s += '三十'; break;
    default:s += nStr2[Math.floor(d/10)]; s += nStr1[d%10];
    }
    return(s);
}
function solarDay1(){
    var sDObj = new Date(SY,SM,SD);
    var lDObj = new Lunar(sDObj);
    return(Animals[(SY-4)%12]+cyclical(lDObj.monCyl)+'月 '+cyclical(lDObj.dayCyl++)+'日');
}
function solarDay2(){
    var sDObj = new Date(SY,SM,SD);
    var lDObj = new Lunar(sDObj);
    return(cyclical(SY-1900+36)+'年 '+cDay(lDObj.month,lDObj.day));
}

function solarDay3(yyyy,mm,dd){
    SY=yyyy;
    SM=mm;
    SD=dd;
    var sTermInfo = new Array(0,21208,42467,63836,85337,107014,128867,150921,173149,195551,218072,240693,263343,285989,308563,331033,353350,375494,397447,419210,440795,462224,483532,504758)
    var solarTerm = new Array("小寒","大寒","立春","雨水","惊蛰","春分","清明","谷雨","立夏","小满","芒种","夏至","小暑","大暑","立秋","处暑","白露","秋分","寒露","霜降","立冬","小雪","大雪","冬至")
var lFtv = new Array("0101*春节","0102 春节后一天","0114 元宵节前一天","0115 元宵节","0116 元宵节后一天","0504 端午节前一天","0505 端午节","0506 端午节后一天","0706 七夕节前一天","0707 七夕情人节","0708 七夕节后一天","0714 中元节前一天","0715 中元节","0716 中元节后一天","0814 中秋节前一天","0815 中秋节","0816 中秋节后一天","0908 重阳节前一天","0909 重阳节","0910 重阳节后一天","1207 腊八节前一天","1208 腊八节","1209 腊八节后一天","1223 小年前一天","1224 小年","1225 小年后一天","1229 除夕前一天","1230*除夕")
         var sFtv = new Array("0101*元旦","0102 元旦后一天","0213 情人节前一天","0214 情人节","0215 情人节后一天","0307 妇女节前一天","0308 妇女节","0309 妇女节后一天","0311 植树节前一天","0312 植树节","0313 植树节后一天","0430 劳动节前一天","0501 劳动节","0502 劳动节后一天","0503 青年节前一天","0504 青年节","0505 青年节后一天","0531 儿童节前一天","0601 儿童节","0602 儿童节后一天","0910中秋节前两天","0911中秋节前一天","0912 中秋节","0927世界旅游日","0930 国庆节前一天","1001 国庆节","1002 国庆节","1003国庆节","1004国庆节","1005国庆节","1006国庆节","1007国庆节","1224 圣诞夜","1225 圣诞节","1226 圣诞节后一天","1231 元旦前一天")



    var sDObj = new Date(yyyy,mm,dd);
    var lDObj = new Lunar(sDObj);
    var lDPOS = new Array(3)
    var festival='',solarTerms='',solarFestival='',lunarFestival='',tmp1,tmp2;
    //农历节日
    for(i in lFtv)
    if(lFtv[i].match(/^(\d{2})(.{2})([\s\*])(.+)$/)) {
       tmp1=Number(RegExp.$1)-lDObj.month
       tmp2=Number(RegExp.$2)-lDObj.day
       if(tmp1==0 && tmp2==0) lunarFestival=RegExp.$4
    }
   
    //国历节日
    for(i in sFtv)
    if(sFtv[i].match(/^(\d{2})(\d{2})([\s\*])(.+)$/)){
       tmp1=Number(RegExp.$1)-(SM+1)
       tmp2=Number(RegExp.$2)-SD
       if(tmp1==0 && tmp2==0) solarFestival = RegExp.$4
    }
    //节气
    tmp1 = new Date((31556925974.7*(SY-1900)+sTermInfo[SM*2+1]*60000)+Date.UTC(1900,0,6,2,5))
    tmp2 = tmp1.getUTCDate()
    if (tmp2==SD)
        solarTerms = solarTerm[SM*2+1]
    tmp1 = new Date((31556925974.7*(SY-1900)+sTermInfo[SM*2]*60000)+Date.UTC(1900,0,6,2,5))
    tmp2= tmp1.getUTCDate()
    if (tmp2==SD)
        solarTerms = solarTerm[SM*2]
   
    //festival =solarTerms + ' ' + solarFestival + ' ' + lunarFestival;
    //alert(lunarFestival)
    if(solarFestival!=""){
        festival=solarFestival;
    }else if(lunarFestival!=""){
        festival=lunarFestival;
    }else if(solarTerms!=""){
        festival=solarTerms
    }else if(SY==curYear && SM==curMonth){
        if(SD==curDay){
            festival="今天"
        }
        if(SD-curDay==1){
            festival="明天"
        }
        if(SD-curDay==2){
            festival="后天"
        }
    }else if(SY==curYear && SM==curMonth+1){
        var ttd=monthDay(SM-1)+parseInt(SD);
        if(ttd-curDay==1){
            festival="明天"
        }
        if(ttd-curDay==2){
            festival="后天"
        }
    }
    return(festival);
}

function monthDay(m){
    var ry=30
     if(m==1){// 判断闰年2月
        if((curYear%4==0 && curYear%100!=0) || curYear%400==0){
            ry=29;
        }else{
            ry=28;
        }
    }else if((m%2==0 && m<7) ||(m>=7 && m%2==1)){
        ry=31;
    }
    return ry;
}

function drawMonth(y,m,day){

    if($(dateObj).attr("rel")==2){//修正第二的日期跨月选取后不能选择上个月的日期
        //alert(m+","+$(dateObj).prev().children("input").val().split("-")[1])
        if(m==$(dateObj).prev().children("input").val().split("-")[1])
            m-=1;   
    }
   
   
    var x=new Date(y,m,1);
    m=x.getMonth();
    y=x.getFullYear();
    var x2=new Date(y,m+1,1);
    var y2=x2.getFullYear();
    var m2=x2.getMonth();
   

    var ss=str1=str2='<tr class="line2"><th class="xx">日</th><th>一</th><th>二</th><th>三</th><th>四</th><th>五</th><th class="xx">六</th></tr>';
    for(var i=0;i<6;i++){
        str1+="<tr>";
        str2+="<tr>"
        for(var j=1;j<8;j++){
            if(j==1 || j==7){
                ss='class="xx"';
            }
            str1+='<td id="tf'+(i*7+j)+'" '+ss+'></td>'
            str2+='<td id="ts'+(i*7+j)+'" '+ss+'></td>'
            ss="";
        }
        str1+="</tr>"
        str2+="</tr>"
    }
   
    $("#prevMonth").empty().append(str1);
    $("#nextMonth").empty().append(str2);
    $("#prevDate")[0].innerHTML=y+"年"+(m+1)+"月";
    $("#nextDate")[0].innerHTML=y2+"年"+(m2+1)+"月";
    var d=1;
    week=x.getDay();
    while (x.getMonth() != m2) {
        d2=parseInt(d+week);
        $("#tf"+d2).attr("value",y+'-'+o2f(m+1)+"-"+o2f(d)).text(d);
        var ddd=new Date(y,m,d);
        if($(dateObj).attr("rel")==2){
            if(ddd-startDate<0){
                $("#tf"+d2).addClass("out");
            }
            if(ddd-endDate>0){
                $("#tf"+d2).addClass("out");
            }
            if(day==d){
                $("#tf"+d2).addClass("select");
            }
        }
        if(y==curYear&&m==curMonth && curDay==d)
            $("#tf"+d2).addClass("today");
        if(ddd-now<0)
            $("#tf"+d2).addClass("out");
        if(ddd-maxd>0)
            $("#tf"+d2).addClass("out");
        if(day==d){
            $("#tf"+d2).addClass("select");
        }
        x.setDate(++d);
    }
    d=1;
    week=x2.getDay();
    m2+=1;
    var x3=new Date(y,m2,1)
    m2=x3.getMonth();
    while (x2.getMonth() != m2) {
        d2=parseInt(d+week);
        $("#ts"+d2).attr("value",y+'-'+o2f(m2==0?12:m2)+"-"+o2f(d)).text(d);
        if($(dateObj).attr("rel")==2 && endDate>2){
            if(m2-1>endM || (m2-1)==endM && d>=endD){
                $("#ts"+d2).addClass("out");
            }
        }else{   
            if((y2==maxYear && (m2-1)>maxMonth) || (y2==maxYear && m2>maxMonth && d2>maxDay))
                $("#ts"+d2).addClass("out");
            if(y==curYear&&m2==curMonth && curDay==d)
                $("#tf"+d2).addClass("select");
        }
        x2.setDate(++d);
       
    }

}

function changeMonth(d){
    tmpMonth+=d
    var x=new Date(curYear,tmpMonth,1);
    m=x.getMonth();
    y=x.getFullYear();
    if(y<curYear || (y==curYear &&curMonth>m) || y>maxYear || y==maxYear && maxMonth==m){
        tmpMonth-=d;
        return;
    }
    if($(dateObj).attr("rel")==2 && endDate>2){
        tmpMonth-=d;
        return;   
    }
    drawMonth(curYear,tmpMonth)
}

function dateClose(){
    $('#datePoint').hide();
}
function resetDate(y,m,d){
    if(y){
        var x=new Date(y,m,d);
        y=x.getFullYear();
        m=x.getMonth();
        d=x.getDate();
        if(y<curYear || (y==curYear &&curMonth>m) || y>maxYear || (y==maxYear && maxMonth+1<m)){
            // 超出了规定的选择范围,采用默认选择
        }else if(y==maxYear && maxMonth+1==m && maxDay>d){
            drawMonth(y,maxMonth,d)
            tmpMonth=11+curMonth;
            return ;
        }else{
            if(y>curYear)
                tmpMonth+=12;
            drawMonth(y,m-1,d);
            tmpMonth=m-1;
            return ;
        }
    }
    drawMonth(curYear,curMonth)
    tmpMonth=curMonth;
}
function initDate(){
    var str='<div id="datePoint">'
            +'<table border="0" cellspacing="0" cellpadding="0" class="line">'
            +'<tr>'
            +'    <th width="13" class="prev"><a href="" id="prev">&lt;</a></th>'
            +'    <th id="prevDate"></th>'
            +'    <th class="line"></th>'
            +'    <th id="nextDate"></th>'
            +'    <th width="13" class="next"><a href="" id="next">&gt;</a></th>'
            +' </tr>'
            +' <tr>'
            +'    <td colspan="2"><table border="0" cellspacing="0" cellpadding="0" id="prevMonth">'
            +'    </table></td>'
            +'    <td class="line"></td>'
            +'    <td colspan="2"><table border="0" cellspacing="0" cellpadding="0" id="nextMonth">'
            +'    </table></td>'
            +' </tr>'
            +' <tr>'
            +'    <td colspan="5" class="back"><a href="" id="dateClose">关闭</a></td>'
            +' </tr>'
            +'</table>'

    $("body").append(str);
   
    /*var dd =$(".inputDate:first input").val().split("-");
    now = new Date(dd[0],dd[1]-1,dd[2]);*/
    now=new Date();
    curDay=now.getDate();
    curMonth=now.getMonth();
    curYear=now.getFullYear();
    maxd= new Date(curYear+1,curMonth,curDay);
    maxDay=maxd.getDate();
    maxMonth=maxd.getMonth();
    maxYear=maxd.getFullYear();
    tmpMonth=curMonth;
   
   
    $('.inputDate').each(function(){
        showDate(this)
    });
    if(typeof(initDateAgain)=="function"){
        initDateAgain.call();   
    }
    $("#prev").click(function(){
        changeMonth(-1);
        return false;
    });
    $("#next").click(function(){
        changeMonth(1);
        return false;
    });
    $("#dateClose").click(function(){
        dateClose();
        return false;
    });
}

function showDate(o){
    var dd1=new Date(curYear,curMonth,curDay+1);
    var dd2=new Date(curYear,curMonth,curDay+2);
    var y1=dd1.getFullYear();
    var m1=dd1.getMonth()
    var d1=dd1.getDate();
    var y2=dd2.getFullYear();
    var m2=dd2.getMonth()
    var d2=dd2.getDate();
    var l=$(o).attr("rel");
    var v=$(o).attr("rev");
    var o2=$("input",o);
    if(l==2){
        $(o2).val(y2+"-"+o2f(m2+1)+"-"+o2f(d2));
    }else{
        $(o2).val(y1+"-"+o2f(m1+1)+"-"+o2f(d1));
    }
    if(v==1){
        if(l==2)
            $("i",o).text(solarDay3(y2,m2,d2));
        else
            $("i",o).text(solarDay3(y1,m1,d1));
    }
   
}

function o2f(n){
    return n>9?n:("0"+n);
}

//alert(solarDay3(2011,10,11))

$(function(){
   
    initDate();
    $(document).click(function(e){
        obj=e.target;
        if($(obj)[0].id!='datePoint' && !$(obj).parents("#datePoint")[0] && !$(obj).parents(".inputDate")[0]){
            $("#datePoint").hide();
        }
    });


    $(".inputDate").click(function(){
        dateObj=this;
        $('#datePoint').show().css({"top":$(this).offset().top+25,"left":$(this).offset().left});
       
        if($(this).parents(".tipsite")[0]){
            $('#datePoint').css("top",$(this).offset().top+50)
        }
       
        var dd=$("input",this).val().split(" ")[0];
        //$("input",this).val("");
        if(dd!=""){
            dd=dd.split("-");
            resetDate(dd[0],dd[1],dd[2]);
        }else{
            resetDate();
        }
    })
    $(".inputDate input").blur(function(){
                                       
        var v=$.trim($(this).val());
        if(v==""){
            showDate($(this).parent())
        }
    });
    $('#prevMonth,#nextMonth').click(function(e){
        var c=e.target.className;
        var n=e.target.nodeName;
        var v=$(e.target).attr("value");
        if(c=='out' || c=='xx out'){
            return false;
        }
        if(n!='TD'){
            return false;
        }
        if(v=="" || v==undefined){
            return false;   
        }
       
        var v2=v.split("-");
        var rell=$(dateObj).attr("rel");//是否关联日期
        var rev=$(dateObj).attr("rev");//是否显示农历和节假日
        $("input",dateObj).val(v);
        if(rev==1){
            $("i",dateObj).text(solarDay3(v2[0],v2[1]-1,v2[2]));
        }
        if(rell){
            if(rell==1){
                v2[2]++;
                v2[1]--;
                startDate=new Date(v2[0],v2[1],v2[2]);
                v2[2]+=15; // 关联日期的延后时长
                endDate=new Date(v2[0],v2[1],v2[2]);
                endY=endDate.getFullYear();
                endM=endDate.getMonth();
                endD=endDate.getDate();
                startY=startDate.getFullYear();
                startM=startDate.getMonth();
                startD=startDate.getDate();
                $(".inputDate[rel=2]").children("input").val(startY+"-"+o2f(startM+1)+"-"+o2f(startD));
                if(rev==1)
                    $(".inputDate[rel=2]").children("i").text(solarDay3(startY,startM,startD));
            }
        }
        $('#datePoint').hide();
    });
})

对应的html代码为:

<p class="inputDate" rev="1" rel="1"><label>开始日期:</label><input type="text" value="2011-06-23"  onfocus="this.style.color='#333'" onblur="this.style.color='#999'" /><b class="dateSelect">select</b><i></i></p>

<p class="inputDate" rev="1" rel="21"><label>结束日期:</label><input type="text" value="2011-06-23"  onfocus="this.style.color='#333'" onblur="this.style.color='#999'" /><b class="dateSelect">select</b><i></i></p>

代码解释:

class=“inputDate” 这个是日期标志位,表示点击会调用日期控件,在页面初始化时已经绑定了

rev=“1” 表示当前需要显示节假日, 对应的,<i>就是显示节假日的</i>

rel=“1” 和rel=“2” 表示,这住日期是有关联的,结束日期会根据开始日期的选择确认起始选择日期。结束日期可以设定一段可选的日期范围,这里默认是15天。
分享到:
评论

相关推荐

Global site tag (gtag.js) - Google Analytics