You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在JS中实现网格Hover时获取行列并添加日历事件

问题解决:日历网格悬停获取行列并显示添加按钮

问题分析

原代码存在几个关键问题:

  1. jQuery的hover()方法第一个参数是mouseenter回调,第二个才是mouseleave,你把逻辑写反了;
  2. .row和.col是同级元素,.row内部没有.col,所以$(this).find(".col")无法找到目标元素;
  3. 现有网格结构用.row和.col做分隔线,没有实际的单元格容器,无法直接监听单个单元格的悬停事件。

解决方案

我们需要先给每个网格单元格添加透明的占位容器,这样既能监听悬停,又能显示“+”按钮,同时准确获取行列信息。

1. 修正HTML结构(添加单元格占位)

在.content里添加单元格容器,每个单元格对应一个时间段和日期:

<div class="container-orario h-full relative antialiased w-full">
  <div class="days" id="classroom_admin-orario-days">
    <div class="filler"></div>
    <div class="filler"></div>
    <div class="day">Lun</div>
    <div class="day">Mar</div>
    <div class="day">Mer</div>
    <div class="day">Gio</div>
    <div class="day">Ven</div>
    <div class="day">Sab</div>
  </div>
  <div class="content" id="classroom_admin-orario-content">
    <!-- 时间标签 -->
    <div class="time" style="grid-row:1">08:00</div>
    <div class="time" style="grid-row:2">09:00</div>
    <div class="time" style="grid-row:3">10:00</div>
    <div class="time" style="grid-row:4">11:00</div>
    <div class="time" style="grid-row:5">12:00</div>
    <div class="time" style="grid-row:6">13:00</div>
    <div class="time" style="grid-row:7">14:00</div>
    <div class="filler-col"></div>
    
    <!-- 单元格占位容器:7行 × 6列 -->
    <div class="cell" style="grid-column:3;grid-row:1"></div>
    <div class="cell" style="grid-column:4;grid-row:1"></div>
    <div class="cell" style="grid-column:5;grid-row:1"></div>
    <div class="cell" style="grid-column:6;grid-row:1"></div>
    <div class="cell" style="grid-column:7;grid-row:1"></div>
    <div class="cell" style="grid-column:8;grid-row:1"></div>
    
    <div class="cell" style="grid-column:3;grid-row:2"></div>
    <div class="cell" style="grid-column:4;grid-row:2"></div>
    <div class="cell" style="grid-column:5;grid-row:2"></div>
    <div class="cell" style="grid-column:6;grid-row:2"></div>
    <div class="cell" style="grid-column:7;grid-row:2"></div>
    <div class="cell" style="grid-column:8;grid-row:2"></div>
    
    <div class="cell" style="grid-column:3;grid-row:3"></div>
    <div class="cell" style="grid-column:4;grid-row:3"></div>
    <div class="cell" style="grid-column:5;grid-row:3"></div>
    <div class="cell" style="grid-column:6;grid-row:3"></div>
    <div class="cell" style="grid-column:7;grid-row:3"></div>
    <div class="cell" style="grid-column:8;grid-row:3"></div>
    
    <div class="cell" style="grid-column:3;grid-row:4"></div>
    <div class="cell" style="grid-column:4;grid-row:4"></div>
    <div class="cell" style="grid-column:5;grid-row:4"></div>
    <div class="cell" style="grid-column:6;grid-row:4"></div>
    <div class="cell" style="grid-column:7;grid-row:4"></div>
    <div class="cell" style="grid-column:8;grid-row:4"></div>
    
    <div class="cell" style="grid-column:3;grid-row:5"></div>
    <div class="cell" style="grid-column:4;grid-row:5"></div>
    <div class="cell" style="grid-column:5;grid-row:5"></div>
    <div class="cell" style="grid-column:6;grid-row:5"></div>
    <div class="cell" style="grid-column:7;grid-row:5"></div>
    <div class="cell" style="grid-column:8;grid-row:5"></div>
    
    <div class="cell" style="grid-column:3;grid-row:6"></div>
    <div class="cell" style="grid-column:4;grid-row:6"></div>
    <div class="cell" style="grid-column:5;grid-row:6"></div>
    <div class="cell" style="grid-column:6;grid-row:6"></div>
    <div class="cell" style="grid-column:7;grid-row:6"></div>
    <div class="cell" style="grid-column:8;grid-row:6"></div>
    
    <div class="cell" style="grid-column:3;grid-row:7"></div>
    <div class="cell" style="grid-column:4;grid-row:7"></div>
    <div class="cell" style="grid-column:5;grid-row:7"></div>
    <div class="cell" style="grid-column:6;grid-row:7"></div>
    <div class="cell" style="grid-column:7;grid-row:7"></div>
    <div class="cell" style="grid-column:8;grid-row:7"></div>
    
    <!-- 原有分隔线 -->
    <div class="col" style="grid-column:3"></div>
    <div class="col" style="grid-column:4"></div>
    <div class="col" style="grid-column:5"></div>
    <div class="col" style="grid-column:6"></div>
    <div class="col" style="grid-column:7"></div>
    <div class="col" style="grid-column:8"></div>
    <div class="row" style="grid-row:1"></div>
    <div class="row" style="grid-row:2"></div>
    <div class="row" style="grid-row:3"></div>
    <div class="row" style="grid-row:4"></div>
    <div class="row" style="grid-row:5"></div>
    <div class="row" style="grid-row:6"></div>
    <div class="row" style="grid-row:7"></div>
    
    <!-- EVENT LIST -->
    <div class="event calendar1" style="grid-column: 3;grid-row: 2/span 2; ">Matematica<br><span class="time-subtitle">08:00 - 10:00</span></div>
    <div class="event calendar2" style="grid-column: 3;grid-row: 4/span 1;">Sistemi e Reti<br><span class="time-subtitle">10:00 - 11:00</span></div>
    <div class="event calendar3" style="grid-column: 3;grid-row: 5/span 1;">Educazione Fisica<br><span class="time-subtitle">11:00 - 12:00</span></div>
    <div class="event calendar4" style="grid-column: 3;grid-row: 6/span 1;">Inglese<br><span class="time-subtitle">12:00 - 13:00</span></div>
    <div class="event calendar5" style="grid-column: 3;grid-row: 7/span 1;">Italiano<br><span class="time-subtitle">13:00 - 14:00</span></div>
  </div>
</div>
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>

2. 添加CSS样式(实现悬停显示“+”)

给单元格添加透明背景和悬停样式,同时设置事件层级低于原有事件:

/* 原有CSS保持不变,新增以下内容 */
.cell {
  position: relative;
  z-index: 1; /* 低于event的层级,避免遮挡事件 */
}

.cell:hover {
  background-color: rgba(0,0,0,0.05);
}

.cell:hover::after {
  content: "+";
  position: absolute;
  top: 50%;
  left: 50%;
  transform: translate(-50%, -50%);
  font-size: 2em;
  color: #217346;
  font-weight: bold;
}

3. 修正JavaScript代码(获取行列信息)

直接监听每个.cell的悬停事件,提取对应的网格行列:

// 监听所有单元格的悬停事件
$(".cell").hover(function() {
  // 获取当前单元格的网格行和列(通过getComputedStyle获取)
  const style = window.getComputedStyle(this);
  const gridRow = style.gridRowStart;
  const gridCol = style.gridColumnStart;
  
  // 转换为用户友好的序号(列从1开始对应Lun到Sab)
  const dayIndex = parseInt(gridCol) - 2; // 因为gridColumn从3开始,对应第1天
  const timeIndex = parseInt(gridRow);
  
  console.log(`行(时间段): ${timeIndex} 列(星期): ${dayIndex}`);
});

关键说明

  • 新增的.cell元素作为透明占位,不会影响原有布局,但能准确捕捉悬停事件;
  • 通过getComputedStyle直接读取网格的行列值,比通过DOM索引更可靠,避免DOM结构变化导致的错误;
  • 悬停时显示的“+”按钮通过CSS伪元素实现,无需额外DOM元素,保持结构简洁。

内容的提问来源于stack exchange,提问作者Matteo

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.21 06:45:54