百度地图这个应用上,有个点击了某个地点后,会在底部弹出一个滑动面板,这个面板可以滑动,然后我就是使用了js代码,制作了一个功能一样的、h5页面上的滑动面板。
首先html定义一个div作为滑动面板。
这个div之所以能够滑动,其实就是改变了他的top属性和height属性,当top减少1px,height增加1px时,他看上去就是被拖上去了1px。
所以我们只需要捕捉到移动端的单击、滑动、离开等动作,就可以进行判断该如果去控制滑动面板的属性了。而捕捉那些动作的api是也是现成的。也就是touchstart,touchmove和touchend三个。接下来上关键代码:
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8" /> <meta name="viewport" content="width=device-width, user-scalable=no, initial-scale=1, maximum-scale=1" /> <meta name="viewport" content="width=device-width, initial-scale=1.0" /> <title>使用js代码制作H5页面的底部滑动面板。</title> <script type="text/javascript" src="jquery-1.10.2.min.js"></script> </head> <body> <a class="easyui-linkbutton" style=" display: block; height: 100px; width: 100%; text-align: center; border: #eee solid 1px; background-color: antiquewhite; " ><b style="width: 500px; text-align: center; font-size: 16px;">面板, 注意这是移动端页面下效果,使用Google Chrome F12 进行调试</b></a > <div id="slideBoard" style="background-color: #0fffff; left: 0px; width: 100%; position: absolute; height: 50px; " > </div> <script type="text/javascript"> var countClick = 1; //按钮点击次数 var initRate = 0.75; // 滑动面板初始显示比例 var mobileOldY = 0; //手机端记录初始点击y轴的值 var moblieTop = 0; //记录初始点击时滑板的top值 var mobileOldTIME = new Date().getTime();//记录初始点的时间 //PC阻止滚动条 //document.documentElement.style.overflowY = 'hidden'; var slideBoard = document.getElementById("slideBoard"); slideBoard.style.top = Math.ceil($(window).height() * initRate) + "px"; slideBoard.style.height = Math.ceil($(window).height() * (1 - initRate)) + "px"; //document.addEventListener("touchstart", touchStart); //Unable to preventDefault inside passive event listener due to target being treated a //浏览器忽略 preventDefault() 就可以第一时间滚动了 window.addEventListener("touchstart", touchStart, { passive: false }); //滑动开始事件 mobile function touchStart(e) { if(countClick == 1 && e.touches[0].clientY >= parseInt(slideBoard.style.top)){ mobileOldY = e.touches[0].clientY; moblieTop = parseInt(slideBoard.style.top); mobileOldTIME = new Date().getTime(); // document.addEventListener('touchmove', touchMove); // document.addEventListener('touchend', touchEnd); //Unable to preventDefault inside passive event listener due to target being treated a //浏览器忽略 preventDefault() 就可以第一时间滚动了 window.addEventListener("touchmove", touchMove, { passive: false }); window.addEventListener("touchend", touchEnd, { passive: false }); } } function touchMove(e){ e.preventDefault(); var y = e.touches[0].clientY - mobileOldY; slideBoard.style.top = moblieTop + y + "px"; slideBoard.style.height = $(window).height() - y - moblieTop + "px"; if (parseInt(slideBoard.style.top) < 0) { slideBoard.style.top = 0; } if (parseInt(slideBoard.style.top) > Math.ceil($(window).height() * initRate)) { slideBoard.style.top = Math.ceil($(window).height() * initRate) + "px"; slideBoard.style.height = Math.ceil($(window).height() * (1 - initRate)) + "px"; } } function touchEnd(e){ document.removeEventListener('touchmove', touchMove); document.removeEventListener('touchend', touchEnd); var dist = mobileOldY - e.changedTouches[0].clientY; var time = new Date().getTime() - mobileOldTIME; if(dist/time > 0.5){ moveSlideBoardTo(2); return; } if(dist/time < -0.5){ moveSlideBoardTo(0); return; } if(parseInt(slideBoard.style.top) < Math.ceil($(window).height() * 0.1) ){ moveSlideBoardTo(2); }else if(parseInt(slideBoard.style.top) < Math.ceil($(window).height() * 0.5) ){ moveSlideBoardTo(1); }else{ moveSlideBoardTo(0); } } var loopCount = 0; var loopID; //移动滑板到某位置 mobile PC function moveSlideBoardTo(location) { var moveTime = 100; var moveIntervalTime = 10; var locationRate = 1; var rate = moveTime / moveIntervalTime; loopCount = 0; if (location == 0) { locationRate = 0.25; } else if (location == 1) { locationRate = 0.75; } else { locationRate = 1; } if (Math.ceil((1 - locationRate) * $(window).height()) == parseInt(slideBoard.style.top)) { return; } else if (Math.ceil((1 - locationRate) * $(window).height()) < parseInt(slideBoard.style.top)) { //需要上升 var dist = parseInt(slideBoard.style.top) - (1 - locationRate) * $(window).height(); var perdist = Math.ceil(dist / rate); loopID = setInterval("moveUp(" + perdist + "," + rate + "," + locationRate + ")", moveIntervalTime); } else { //下降 var dist = (1 - locationRate) * $(window).height() - parseInt(slideBoard.style.top); var perdist = Math.ceil(dist / rate); loopID = setInterval("moveDown(" + perdist + "," + rate + "," + locationRate + ")", moveIntervalTime); } } //上移函数 function moveUp(perdist, rate, locationRate) { if (loopCount != rate) { slideBoard.style.top = parseInt(slideBoard.style.top) - perdist + "px"; slideBoard.style.height = $(window).height() - parseInt(slideBoard.style.top) + "px"; loopCount = loopCount + 1; } else { slideBoard.style.top = Math.ceil((1 - locationRate) * $(window).height()) + "px"; slideBoard.style.height = $(window).height() - parseInt(slideBoard.style.top) + "px"; clearInterval(loopID); } } //下移函数 function moveDown(perdist, rate, locationRate) { if (loopCount != rate) { slideBoard.style.top = parseInt(slideBoard.style.top) + perdist + "px"; slideBoard.style.height = $(window).height() - parseInt(slideBoard.style.top) + "px"; loopCount = loopCount + 1; } else { slideBoard.style.top = Math.ceil((1 - locationRate) * $(window).height()) + "px"; slideBoard.style.height = $(window).height() - parseInt(slideBoard.style.top) + "px"; clearInterval(loopID); } } </script> </body> </html>
其中moveSlideBoardTo函数是让滑动面板的top等于某个特定的值的,因为我想学百度地图那样,使滑动面板会移动到固定的3个位置,其实分别就是初始位置、80%的位置,
和顶部。
这段代码的逻辑主要就是当手触屏的时候开始判断是否落在面板区域内,如果是的话,手指如果滑动,就进行跟着手指使面板的top和height属性进行相同变化,这样就看上去
是跟着手指在动了。
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 阿里最新开源QwQ-32B,效果媲美deepseek-r1满血版,部署成本又又又降低了!
· AI编程工具终极对决:字节Trae VS Cursor,谁才是开发者新宠?
· 开源Multi-agent AI智能体框架aevatar.ai,欢迎大家贡献代码
· Manus重磅发布:全球首款通用AI代理技术深度解析与实战指南
· 被坑几百块钱后,我竟然真的恢复了删除的微信聊天记录!