项目仓库:
Gitee:https://gitee.com/yyt363045841/klinechart
Github:https://github.com/363045841/klinechart
NPM:https://www.npmjs.com/package/@363045841yyt/klinechart
安装:npm i @363045841yyt/klinechart
项目持续更新中!欢迎提出宝贵建议!如果对您有帮助可以给个 Star!
正常情况下组件内的拖动是通过 overflow-x: auto 来实现的,但是 K 线图通常采用左右拖动的形式浏览,这就要求桌面端和移动端的操作逻辑一致。
视觉层
首先隐藏掉 x 轴滚动条(虽然滚动条看不见也点不到了,但这个 div 依然具备滚动的能力,比如你用触控板双指滑动,或者通过 JS 代码修改 scrollLeft,它依然会滚动):
/* Firefox */
scrollbar-width: none;
/* Chrome/Safari */
::-webkit-scrollbar { display: none; }
逻辑层
mouseDown 事件
当按下左键时,响应事件并记录当前鼠标位置:
function onMouseDown(e: MouseEvent) {
// 只响应左键
if (e.button !== 0) return
const container = containerRef.value
if (!container) return
isDragging.value = true
dragStartX = e.clientX
scrollStartX = container.scrollLeft
// 防止选中文字
e.preventDefault()
}
通过 MouseEvent.button 可以获取鼠标哪个键被按下:
0:主按键,通常指鼠标左键或默认值
1:辅助按键,通常指鼠标滚轮中键
2:次按键,通常指鼠标右键
3:第四个按钮,通常指浏览器后退按钮
4:第五个按钮,通常指浏览器的前进按钮
设置 isDragging 表明开始拖拽。记录鼠标按下时的 X 坐标位置 dragStartX。
保存容器当前的滚动位置 scrollStartX。
mouseMove 事件
function onMouseMove(e: MouseEvent) {
if (!isDragging.value) return
const container = containerRef.value
if (!container) return
const deltaX = dragStartX - e.clientX
container.scrollLeft = scrollStartX + deltaX
}
当鼠标移动时,不断进行以下计算:
计算鼠标动了多少:
位移 = 刚按下时的鼠标 X − 现在的鼠标 X ( 1 ) 位移 = 刚按下时的鼠标 X - 现在的鼠标 X\;(1) 位移=刚按下时的鼠标X−现在的鼠标X(1)
更新卷轴位置:
新的卷轴位置 = 刚按下时的卷轴位置 + 位移 新的卷轴位置 = 刚按下时的卷轴位置 + 位移 新的卷轴位置=刚按下时的卷轴位置+位移
这里的核心问题是要理解当鼠标向左拖动的时候,实际上的 scrollLeft 是应该增加的,因为视觉上用户其实是在向右移动。因此 (1) 式也是向左移动为正,向右移动为负。
mouseUp 事件
function onMouseUp() {
isDragging.value = false
}
取消拖动标记。
渲染层
由于鼠标事件动态修改了 container.scrollLeft,因此 @scroll 事件被照常触发,无缝接入原先的重绘逻辑,实现鼠标拖动和重绘的解耦。
样式交互
为了提供更好的用户体验(UX),我们需要在视觉上告知用户该区域是“可拖拽”的。这通常通过 CSS 的 cursor 属性来实现,模拟真实物理世界中“抓取”和“拖动”的动作反馈。
- 默认状态: 当鼠标悬停在图表区域时,光标应变为张开的手掌(grab),暗示用户“此处可以抓取”。
- 激活状态: 当用户按下鼠标进行拖拽时,光标应变为握紧的拳头(grabbing),给予用户“正在拖动中”的反馈。
.chart-container {
/* 提示用户可以抓取 */
cursor: grab;
}
/* 当元素被按下(激活)时 */
.chart-container:active {
/* 提示用户正在抓取移动中 */
cursor: grabbing;
}
这个 active 伪类在元素被激活(鼠标按下且未松开)时触发。
注意为了防止出现 CSS 规则不生效的情况,应该遵循LVHA原则:
- Link(没点过)
- Visited(点过)
- Hover(鼠标放上去)
- Active(按下去)
3856

被折叠的 条评论
为什么被折叠?



