js实现双日历
实现双日历的基础结构
使用HTML创建两个日历容器,分别用于显示起始日期和结束日期。CSS确保两个日历并排显示,样式保持一致。
<div class="calendar-container">
<div id="calendar-start"></div>
<div id="calendar-end"></div>
</div>
.calendar-container {
display: flex;
gap: 20px;
}
#calendar-start,
#calendar-end {
width: 300px;
border: 1px solid #ddd;
padding: 10px;
}
动态生成日历逻辑
通过JavaScript生成单月日历,支持切换月份。核心逻辑包括计算月份天数、渲染日期格子,并绑定事件处理函数。

function generateCalendar(containerId, year, month) {
const container = document.getElementById(containerId);
const daysInMonth = new Date(year, month + 1, 0).getDate();
const firstDay = new Date(year, month, 1).getDay();
let html = `<div class="header">${year}年${month + 1}月</div>`;
html += '<div class="days-grid">';
// 填充空白格子(月初偏移)
for (let i = 0; i < firstDay; i++) {
html += '<div class="day empty"></div>';
}
// 填充日期格子
for (let day = 1; day <= daysInMonth; day++) {
html += `<div class="day" data-day="${day}">${day}</div>`;
}
container.innerHTML = html;
}
双日历联动与日期选择
初始化两个日历并实现联动逻辑:选择起始日期后自动聚焦结束日期日历,且结束日期不得早于起始日期。

let startDate = null;
let endDate = null;
function initDualCalendar() {
const now = new Date();
generateCalendar('calendar-start', now.getFullYear(), now.getMonth());
generateCalendar('calendar-end', now.getFullYear(), now.getMonth() + 1);
// 绑定日期点击事件
document.querySelectorAll('#calendar-start .day').forEach(day => {
day.addEventListener('click', () => {
startDate = new Date(now.getFullYear(), now.getMonth(), parseInt(day.dataset.day));
updateSelection('calendar-start', day);
});
});
document.querySelectorAll('#calendar-end .day').forEach(day => {
day.addEventListener('click', () => {
if (!startDate) return;
const selectedDate = new Date(now.getFullYear(), now.getMonth() + 1, parseInt(day.dataset.day));
if (selectedDate >= startDate) {
endDate = selectedDate;
updateSelection('calendar-end', day);
}
});
});
}
function updateSelection(calendarId, selectedElement) {
// 清除旧选中状态
document.querySelectorAll(`#${calendarId} .day.selected`).forEach(el => {
el.classList.remove('selected');
});
selectedElement.classList.add('selected');
}
月份切换功能
添加按钮支持向前/向后切换月份,并同步更新两个日历的显示。
function addMonthSwitchers() {
const startPrev = document.createElement('button');
startPrev.textContent = '<';
startPrev.addEventListener('click', () => switchMonth('calendar-start', -1));
const startNext = document.createElement('button');
startNext.textContent = '>';
startNext.addEventListener('click', () => switchMonth('calendar-start', 1));
document.getElementById('calendar-start').prepend(startPrev, startNext);
}
function switchMonth(calendarId, offset) {
const header = document.querySelector(`#${calendarId} .header`);
const [year, month] = header.textContent.match(/\d+/g).map(Number);
const newMonth = month - 1 + offset;
generateCalendar(calendarId, newMonth < 0 ? year - 1 : year, (newMonth + 12) % 12);
}
样式优化与交互反馈
通过CSS增强视觉反馈,例如高亮选中日期、禁用无效日期。
.day {
padding: 5px;
cursor: pointer;
}
.day.selected {
background-color: #007bff;
color: white;
}
.day.disabled {
color: #ccc;
cursor: not-allowed;
}






