摘要:第一部分是正方體部分,第二部分是中的路徑動畫了,第三部分則是交互旋轉(zhuǎn)。然后在立方體元素上添加鼠標(biāo)點擊事件事件,在回調(diào)函數(shù)中做處理內(nèi)容?;卣{(diào)函數(shù)中先記錄下來鼠標(biāo)點擊的位置。
1.前言
我使用了jquery編寫交互的旋轉(zhuǎn),因為初學(xué)所以不太承受,還請見諒。樣式我是寫stylus編碼,自動生成css。
2.正文先放上一張效果圖
我將其分成三部分。第一部分是正方體部分(SVG),第二部分是svg中的路徑動畫了(animateMotion + jQuery),第三部分則是交互旋轉(zhuǎn)(jQuery)。
1.正方體做一個正方體
我的思路是用六塊svg正方形畫板通過css屬性旋轉(zhuǎn)和平移來構(gòu)成正方體。
html代碼:
stylus代碼
html margin 0 padding 0 height 100% width 100% body height 100% width 100% .page .state height 300px width 300px position absolute top 50% left 50% transform translate(-50%,-50%)//修正位置 .container transform-style preserve-3d position relative height 300px width 300px transform rotateX(0deg) rotateY(0deg) svg position absolute height 300px width 300px stroke-width 5px stroke brown fill transparent //填充用透明 .rect height 300px width 300px .top transform rotateX(90deg) translateZ(150px) .bottom transform rotateX(-90deg) translateZ(150px) .left transform rotateY(-90deg) translateZ(150px) .right transform rotateY(90deg) translateZ(150px) .front transform rotateY(0deg) translateZ(150px) .behind transform rotateY(180deg) translateZ(150px)
通常有兩種方式來構(gòu)建一個立方體
第一種:先平移再旋轉(zhuǎn)。優(yōu)點是不許太強的空間構(gòu)造能力,寫起來比較簡單。缺點就是:代碼數(shù)會多一些,需要在平移后設(shè)置旋轉(zhuǎn)基點。替換一下樣式就行。
.top fill blue transform-origin: bottom transform translateY(-200px) rotateX(90deg) .bottom fill red transform-origin:top transform translateY(200px) rotateX(-90deg) .left fill green transform-origin: right transform translateX(-200px) rotateY(-90deg) .right fill black transform-origin: left transform translateX(200px) rotateY(90deg) .front fill grey transform translateZ() .behind fill pink transform translateZ(-200px)
第二種:先旋轉(zhuǎn)再平移。這個的特點就是與上面的相反了。(我使用的是這種)
兩種生成立方體的原理看下圖
第一種
第二種
以上就是兩種構(gòu)建立方體的方法大致原理了
路徑動畫我是通過在相鄰兩個面上一個動畫結(jié)束的位置和下一個動畫起始位置重合,
下一個動畫起始的延時設(shè)置為之前所有動畫的動畫時間,做到視覺認(rèn)為路線是連接起來的。
先上代碼:
路徑動畫是有animateMotion元素做的所以可以不是直線,只是為了方便設(shè)計,我吧path路徑設(shè)計成了直線
有興趣的可以自己設(shè)計一下。
路徑是我用 Method Draw 畫的 editor.method.ac/
接下來就是重點的路徑控制了
$(document).ready(function () { const animate = document.getElementsByTagName("animateMotion"); // 0 frontY 1 frontX 2 behindY 3 behindX 4 leftX 5 rightX 6 topY 7 bottomY var frontY = animate[0], frontX = animate[1], behindY = animate[2], behindX = animate[3], leftX = animate[4], rightX = animate[5], topY = animate[6], bottomY = animate[7]; // Y面球體運動 (() => { //先執(zhí)行一次 frontY.beginElement(); setTimeout(() => { bottomY.beginElement(); }, 3000); setTimeout(() => { behindY.beginElement(); }, 6000); setTimeout(() => { topY.beginElement(); }, 9000); // 循環(huán)執(zhí)行動畫 var time = setInterval(() => { frontY.beginElement(); setTimeout(() => { bottomY.beginElement(); }, 3000); setTimeout(() => { behindY.beginElement(); }, 6000); setTimeout(() => { topY.beginElement(); }, 9000); }, 12000); })(); // X面球體運動 (() => { //先執(zhí)行一次 frontX.beginElement(); setTimeout(() => { leftX.beginElement(); }, 3000); setTimeout(() => { behindX.beginElement(); }, 6000); setTimeout(() => { rightX.beginElement(); }, 9000); // 循環(huán)執(zhí)行動畫 var time = setInterval(() => { frontX.beginElement(); setTimeout(() => { leftX.beginElement(); }, 3000); setTimeout(() => { behindX.beginElement(); }, 6000); setTimeout(() => { rightX.beginElement(); }, 9000); }, 12000); })(); })
我設(shè)置的是讓animateMotion元素的起始值begin為infinite,在頁面加載完畢后動畫不會自動執(zhí)行。
我用jQuery來控制動畫的執(zhí)行順序。
首先獲取每個動畫元素const animate = document.getElementsByTagName("animateMotion");,之后將每個動畫元素都標(biāo)記好。
接著使用計時器setInterval和setTimeout計時器來控制動畫。首先使用setInterval來控制動畫循環(huán)執(zhí)行。接著在setInterval中用setTimeout設(shè)置動畫執(zhí)行的順序,每個setTimeout計時器的延遲都為之前所有動畫時間之和。模塊化的最好先設(shè)置一個動畫對象數(shù)組,然后將動畫順序加入數(shù)組。
最后附加兩個API
// svg指當(dāng)前svg DOM元素 // 暫停 svg.pauseAnimations(); // 重啟動 svg.unpauseAnimations()
兩個API可已暫停當(dāng)前動畫,關(guān)于詳情請看張鑫旭大佬的文章鑫空間
3.旋轉(zhuǎn)控制旋轉(zhuǎn)控制是我還沒完善的地方,用戶體驗不是十分好,還望大佬們幫我指出錯誤。另一個旋轉(zhuǎn)方案過一兩天再添加上來。
代碼:
var X = 0;//記錄X軸旋轉(zhuǎn)過的角度 var Y = 0;//記錄Y軸旋轉(zhuǎn)過的角度 // 旋轉(zhuǎn)控制 $(".container").mousedown(function (event) { var mousedownX = event.clientX; var mousedownY = event.clientY; $("body").mousemove(function (event) { var mousemoveX = event.clientX; var mousemoveY = event.clientY; var scaleY = ((mousemoveX - mousedownX) / 200); var scaleX = ((mousemoveY - mousedownY) / 200); Y = ((Y + scaleY) % 360); X = ((X + scaleX) % 360); $(".container").animate({}, function () { $(".container").css({ "transform": `rotateX(${X}deg) rotateY(${Y}deg)` }); }) }) }) $("body").mouseup(function () { $("body").unbind("mousemove"); $("body").unbind("mousedown"); })
首先設(shè)置兩個變量X,Y這是記錄這個立方體真正旋轉(zhuǎn)了多少角度。
然后在立方體.container元素上添加鼠標(biāo)點擊事件mousedown事件,在回調(diào)函數(shù)中做處理內(nèi)容?;卣{(diào)函數(shù)中先記錄下來鼠標(biāo)點擊的位置。
接著在body上添加鼠標(biāo)移動mousemove事件因為我們移動不能只在立方體上,移動的范圍要擴大到頁面上。接著在移動事件中的回調(diào)函數(shù)做旋轉(zhuǎn)處理,首先記錄下來移動后鼠標(biāo)的位置,計算出鼠標(biāo)移動的距離然后除以一個數(shù)var scaleY = ((mousemoveX - mousedownX) / 200);注意其中的200沒有真正代表的意義,只是因為鼠標(biāo)移動的距離數(shù)值相對于旋轉(zhuǎn)的角度來說比較大,所以除以200減少它移動的角度,可以隨意更改,其中鼠標(biāo)在X軸上移動用戶需要的是圖形在以Y軸旋轉(zhuǎn)。接著我么要計算立方體真正對于初始旋轉(zhuǎn)了多少角度我們最好做一下范圍限制(取模運算),Y = ((Y + scaleY) % 360);最后就是設(shè)置屬性了,先用$(".container").animate()讓旋轉(zhuǎn)用動畫的形式來做成,然后設(shè)置旋轉(zhuǎn)角度$(".container").css({ "transform": rotateX(${X}deg) rotateY(${Y}deg) });用css()方法來設(shè)置旋轉(zhuǎn)角度。
最后將github庫放上來
github庫
文章版權(quán)歸作者所有,未經(jīng)允許請勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。
轉(zhuǎn)載請注明本文地址:http://www.ezyhdfw.cn/yun/103322.html
摘要:前端日報精選源碼解析一組件的實現(xiàn)與掛載寫在的前端數(shù)據(jù)層不完全指北非時圓角邊框剪裁問題專題之解讀排序源碼中的閉包再也不用擔(dān)心面試被問什么是閉包了中文路由路由基礎(chǔ)入門實戰(zhàn)操作詳細(xì)指南前端學(xué)習(xí)教程用實現(xiàn)一門編程語言語言簡介眾成翻譯第 2017-10-19 前端日報 精選 React源碼解析(一):組件的實現(xiàn)與掛載寫在2017的前端數(shù)據(jù)層不完全指北Chrome opacity非1時border...
摘要:元素元素歸屬于容器和結(jié)構(gòu)元素,在文檔內(nèi)允許嵌套使用獨立的片段。如果包含葡萄的組被移動到文檔的末尾,它將出現(xiàn)在西瓜的前面。例如,將葡萄的莖的路徑移動到組的末尾將導(dǎo)致莖在頂部。 作者:DDU(滬江前端開發(fā)工程師)本文是原文翻譯,轉(zhuǎn)載請注明作者及出處。 簡介 Scalable Vector Graphics (SVG)是在XML中描述二維圖形的語言。這些圖形由路徑,圖片和(或)文本組成,并能...
摘要:元素元素歸屬于容器和結(jié)構(gòu)元素,在文檔內(nèi)允許嵌套使用獨立的片段。如果包含葡萄的組被移動到文檔的末尾,它將出現(xiàn)在西瓜的前面。例如,將葡萄的莖的路徑移動到組的末尾將導(dǎo)致莖在頂部。 作者:DDU(滬江前端開發(fā)工程師)本文是原文翻譯,轉(zhuǎn)載請注明作者及出處。 簡介 Scalable Vector Graphics (SVG)是在XML中描述二維圖形的語言。這些圖形由路徑,圖片和(或)文本組成,并能...
摘要:寫在前面的前面現(xiàn)在拍電影搞真人秀都流行拍續(xù)集,哥今天給大家?guī)淼氖谴蛟熳蠲罊C房的續(xù)集,哥的目標(biāo)是成為機房界的網(wǎng)紅。機柜標(biāo)簽機房中最重要的物理資源機柜是機房管理規(guī)劃監(jiān)控人員最關(guān)注的對象之一。 寫在前面的前面 現(xiàn)在拍電影、搞真人秀都流行拍續(xù)集,哥今天給大家?guī)淼氖谴蛟熳蠲?D機房的續(xù)集,哥的目標(biāo)是成為3D機房界的網(wǎng)紅。 -------------------------------我是這個...
閱讀 2678·2023-04-25 17:33
閱讀 715·2021-11-23 09:51
閱讀 3033·2021-07-30 15:32
閱讀 1492·2019-08-29 18:40
閱讀 2023·2019-08-28 18:19
閱讀 1526·2019-08-26 13:48
閱讀 2311·2019-08-23 16:48
閱讀 2353·2019-08-23 15:56