<em>Mac</em>Book项目 2009年学校开始实施<em>Mac</em>Book项目,所有师生配备一本<em>Mac</em>Book,并同步更新了校园无线网络。学校每周进行电脑技术更新,每月发送技术支持资料,极大改变了教学及学习方式。因此2011
2021-06-01 09:32:01
JS 簡單的操作杆旋轉實現
首先說明一下,請直接忽略背景圖,這裡主要實現的是杆旋轉控制方向盤旋轉。
滑鼠移出控制區域,控制球復位
建立 ballOption.js 檔案,用以繫結控制球指定 dom,並初始化相關操作
建立 eleOption.js 檔案,用以實現一些頻繁的 dom 操作
主要是通過滑鼠滑動事件控制“控制球”位置更改及獲取以螢幕上方向為0度的角度計算,來控制“方向盤”進行旋轉。
1、監聽滑鼠滑動的事件,並判斷 event 的 point 是否進入到控制球,如果進入,控制小球隨著滑鼠進行移動。
2、滑鼠劃出控制區域,控制球復位,旋轉角度歸零。
3、判斷滑鼠 point 點位置,通過反三角函數獲取角度。
4、暴露控制球與控制區域中心形成的旋轉角度,觸發外界事件(方向盤旋轉)
ballOption.js 檔案
class BallOption{ //新增操作dom ID eleId //el操作物件 eleOption //控制球物件 ball //控制球尺寸 ballWidth ballHeight ballOffX ballOffY //是否觸碰過控制球 isTouchedBall = false //控制區域 optionRangeView optionRangeViewCenterPoint //上一次角度 lastDeg //角度回撥 angleCallBack //初始化操作 constructor(eleId,angleCallBack){ this.eleId = eleId this.angleCallBack = angleCallBack this.eleOption = new EleOption(eleId) } //建立操作框 createOptionView(){ if(this.eleId != undefined){ this.createOptionRangeView() this.createOptionBallView() } } //繪製操作範圍 createOptionRangeView(){ let width = this.eleOption.getEleWidth(this.eleOption.getCurrentEle()) let height = this.eleOption.getEleHeight(this.eleOption.getCurrentEle()) this.optionRangeView = this.eleOption.createEl('optionRangeViewEl') this.eleOption.addSubEl(this.eleOption.getCurrentEle(),this.optionRangeView) this.eleOption.setBackgroundColor(this.optionRangeView,'rgb(248,248,248)') this.eleOption.setWidth(this.optionRangeView,width) this.eleOption.setHeight(this.optionRangeView,height) this.eleOption.setCircle(this.optionRangeView) //新增拖拽事件 this.eleOption.addMoveEvent(optionRangeViewEl,this,this.makeBallFollowScroll,this.resetBall) } //控制球隨滑鼠滾 makeBallFollowScroll(point,ballOption){ let x = (point.x - ballOption.ballOffX) let y = (point.y - ballOption.ballOffY) let currentPoint = {x,y} if(ballOption.checkIsTouchControlBall(point)){ ballOption.eleOption.setCenter(ballOption.ball,currentPoint) ballOption.getCurrentAngle(point) } } //檢測是否碰觸過控制球 checkIsTouchControlBall(point){ if(!this.isTouchedBall){ let isTouchBall = ( point.x > this.optionRangeViewCenterPoint.x - this.ballWidth && point.x < this.optionRangeViewCenterPoint.x + this.ballWidth && point.y > this.optionRangeViewCenterPoint.y - this.ballHeight && point.y < this.optionRangeViewCenterPoint.y + this.ballHeight ) if(isTouchBall){ this.isTouchedBall = true this.eleOption.setTransparency(this.ball,100) } } return this.isTouchedBall } //滑鼠移出事件 resetBall(ballOption){ ballOption.isTouchedBall = false ballOption.eleOption.setCenter(ballOption.ball,ballOption.optionRangeViewCenterPoint) ballOption.eleOption.setTransparency(ballOption.ball,40) if(ballOption.angleCallBack){ ballOption.lastDeg = 0 ballOption.angleCallBack(ballOption.lastDeg) } } //計算角度 getCurrentAngle(point){ let addX = (point.x - this.eleOption.getEleWidth(this.optionRangeView) / 2.0) let addY = (point.y - this.eleOption.getEleHeight(this.optionRangeView) / 2.0) if(addY != 0){ let tan = addX / addY let angle = Math.atan(tan) this.lastDeg = (angle / Math.PI) * 180 if(addX <= 0 && addY < 0){ this.lastDeg = this.lastDeg } else if(addX <= 0 && addY > 0){ this.lastDeg = (180 - Math.abs(this.lastDeg)) } else if(addX >= 0 && addY > 0){ this.lastDeg = 180 + Math.abs(this.lastDeg) } else if(addX >= 0 && addY < 0){ this.lastDeg = (360 - Math.abs(this.lastDeg)) } } if(this.angleCallBack){ this.angleCallBack(360 - this.lastDeg) } } //繪製球捲動 createOptionBallView(){ let scale = 3.2 this.ballWidth = this.eleOption.getEleWidth(this.eleOption.getCurrentEle()) / scale this.ballHeight = this.eleOption.getEleHeight(this.eleOption.getCurrentEle()) / scale this.ballOffX = this.ballWidth / 2.0 this.ballOffY = this.ballHeight / 2.0 this.ball = this.eleOption.createEl('optionBallViewEl') this.eleOption.addSubEl(this.eleOption.getCurrentEle(),this.ball) this.eleOption.setBackgroundColor(this.ball,'black') this.eleOption.setWidth(this.ball,this.ballWidth) this.eleOption.setHeight(this.ball,this.ballHeight) this.eleOption.setCircle(this.ball) this.eleOption.setSupCenter(this.ball) this.eleOption.cancleUserInreface(this.ball) this.eleOption.setTransparency(this.ball,40) //儲存中心點座標 this.optionRangeViewCenterPoint = this.eleOption.getCenterPoint({offX:this.ballOffX,offY:this.ballOffY}) } }
eleOption.js
class EleOption{ //新增操作dom ID eleId constructor(eleId){ this.eleId = eleId } //獲取當前關聯的el getCurrentEle(){ return document.getElementById(this.eleId) } //獲取el寬度 getEleWidth(el){ return el.offsetWidth } //獲取el高度 getEleHeight(el){ return el.offsetHeight } //設定背景顏色 setBackgroundColor(el,color){ el.style.backgroundColor = color } //設定寬度 setWidth(el,w){ el.style.width = w + 'px' } //設定高度 setHeight(el,h){ el.style.height = h + 'px' } //設定圓角 setCircle(el){ el.style.borderRadius = (this.getEleWidth(el) / 2.0 )+ 'px' } //設定絕對定位 setAbsolutePosition(el){ el.style.position = 'absolute' } //設定透明度 setTransparency(el,alpha){ el.style.opacity = alpha / 100 } //設定為父el中心位置 setSupCenter(el){ if(el.style.position != 'absolute'){ this.setAbsolutePosition(el) let superElWidth = this.getEleWidth(this.getSuperEl(el)) let superElHeight = this.getEleHeight(this.getSuperEl(el)) let width = this.getEleWidth(el) let height = this.getEleHeight(el) el.style.left = ((superElWidth - width) / 2.0) + 'px' el.style.top = ((superElHeight - height) / 2.0) + 'px' } } //設定中心位置 setCenter(el,point){ if(el.style.position != 'absolute'){ this.setAbsolutePosition(el) } el.style.left = point.x + 'px' el.style.top = point.y + 'px' } //獲取父類別el getSuperEl(el){ return el.parentNode } //獲取el getElById(elId){ return document.getElementById(elId) } //建立el createEl(elId){ let el = document.createElement('div') if(elId){ el.setAttribute('id',elId) } return el } //新增子el addSubEl(superEl,subEl){ superEl.appendChild(subEl); } //取消互動 cancleUserInreface(el){ el.style.pointerEvents = 'none' } //新增move事件 addMoveEvent(el,ballOption,mcb,emcb){ //滑鼠進入移動事件 el.onmousemove = (event)=>{ mcb(this.getMoveEventPoint(event,el),ballOption) } //滑鼠移出事件 el.onmouseout = (_)=>{ emcb(ballOption) } } //move事件監聽 getMoveEventPoint(event,el){ let x = event.clientX - this.getSuperEl(el).offsetLeft let y = event.clientY - this.getSuperEl(el).offsetTop return {x,y} } //獲取中心點 getCenterPoint(off){ let x = this.getSuperEl(this.getCurrentEle()).offsetLeft + (this.getEleWidth(this.getCurrentEle()) / 2.0) - off.offX let y = this.getSuperEl(this.getCurrentEle()).offsetTop + (this.getEleHeight(this.getCurrentEle()) / 2.0) - off.offY return {x,y} } }
初始化控制操作類即可,繫結相對應地 dom 進行,控制球的初始化操作
<script src="../js/eleOption.js"></script> <script src="../js/ballOption.js"></script> <body> <div id="optionDiv"></div> <div id="car"> <img src="../source/car.jpeg" alt=""> </div> <div id="target"> <img src="../source/circle.jpeg" alt=""> </div> </body> <script> //初始化控制操作類即可 let ballOption = new BallOption('optionDiv',(angle)=>{ let targetEl = document.getElementById('target') targetEl.style.transform = 'rotate(' + angle + 'deg)' }) ballOption.createOptionView() </script>
程式碼很簡單,其中通過計算來控制小球的位置移動,並將時時的滑鼠滑過的 point 轉換為旋轉角度供外界使用
以上就是JS實現簡單的操作杆旋轉範例詳解的詳細內容,更多關於JS操作杆旋轉的資料請關注it145.com其它相關文章!
相關文章
<em>Mac</em>Book项目 2009年学校开始实施<em>Mac</em>Book项目,所有师生配备一本<em>Mac</em>Book,并同步更新了校园无线网络。学校每周进行电脑技术更新,每月发送技术支持资料,极大改变了教学及学习方式。因此2011
2021-06-01 09:32:01
综合看Anker超能充系列的性价比很高,并且与不仅和iPhone12/苹果<em>Mac</em>Book很配,而且适合多设备充电需求的日常使用或差旅场景,不管是安卓还是Switch同样也能用得上它,希望这次分享能给准备购入充电器的小伙伴们有所
2021-06-01 09:31:42
除了L4WUDU与吴亦凡已经多次共事,成为了明面上的厂牌成员,吴亦凡还曾带领20XXCLUB全队参加2020年的一场音乐节,这也是20XXCLUB首次全员合照,王嗣尧Turbo、陈彦希Regi、<em>Mac</em> Ova Seas、林渝植等人全部出场。然而让
2021-06-01 09:31:34
目前应用IPFS的机构:1 谷歌<em>浏览器</em>支持IPFS分布式协议 2 万维网 (历史档案博物馆)数据库 3 火狐<em>浏览器</em>支持 IPFS分布式协议 4 EOS 等数字货币数据存储 5 美国国会图书馆,历史资料永久保存在 IPFS 6 加
2021-06-01 09:31:24
开拓者的车机是兼容苹果和<em>安卓</em>,虽然我不怎么用,但确实兼顾了我家人的很多需求:副驾的门板还配有解锁开关,有的时候老婆开车,下车的时候偶尔会忘记解锁,我在副驾驶可以自己开门:第二排设计很好,不仅配置了一个很大的
2021-06-01 09:30:48
不仅是<em>安卓</em>手机,苹果手机的降价力度也是前所未有了,iPhone12也“跳水价”了,发布价是6799元,如今已经跌至5308元,降价幅度超过1400元,最新定价确认了。iPhone12是苹果首款5G手机,同时也是全球首款5nm芯片的智能机,它
2021-06-01 09:30:45