- HTML5實(shí)驗(yàn)室
- 張磊編著
- 1096字
- 2019-01-09 15:53:49
實(shí)驗(yàn)3 繪制動(dòng)畫
簡(jiǎn)介
在計(jì)算機(jī)的世界中,有很多東西可以直接看得到,有很多東西已封裝好了,看不到,只能用??吹玫降模罕热?,在實(shí)驗(yàn)2中,設(shè)置小球的顏色和位置,小球的顏色是隨機(jī)產(chǎn)生的,位置是計(jì)算出來的;看不到的:比如,在實(shí)驗(yàn)1中,調(diào)用CanvasRenderingContext2D的beginPath、arc、stroke方法就可以在畫布上畫一個(gè)圓,而看不到各種方法的具體算法和實(shí)現(xiàn),如果不用上述方法,而是自己寫一個(gè)算法去畫一個(gè)圓呢?在自己寫個(gè)畫圓的算法之前,先要了解怎么利用CanvasRenderingContext2D API畫線。
畫線
不用arc方法,自己寫一個(gè)算法來畫圓。在自己寫畫圓的算法之前,首先要了解Canvas RenderingContext2D的moveTo和lineTo方法。
這里需要注意的是HTML DOM Window對(duì)象的moveTo()方法可以把窗口的左上角移動(dòng)到一個(gè)指定的坐標(biāo)。而CanvasRenderingContext2D的moveTo的作用是設(shè)置當(dāng)前位置并開始一條新的子路徑。不能搞混淆了,一個(gè)是window.moveTo,一個(gè)是CanvasRendering Context2D.moveTo。
語(yǔ)法
moveTo(x,y)
moveTo()方法將當(dāng)前位置設(shè)置為(x,y)并用它作為第一點(diǎn)創(chuàng)建一條新的子路徑。除了moveTo(x,y),還需要知道:
lineTo(x,y)
lineTo()方法為當(dāng)前子路徑添加一條直線。這條直線從當(dāng)前點(diǎn)開始,到(x,y)結(jié)束。
最后需要用CanvasRenderingContext2D.stroke方法來連接所有路徑。
通過上面這些知識(shí),可以輕松畫出一個(gè)三角形:
<canvasid="myCanvas"width="200"height="100"style="border:1px solid #c3c3c3;"> Your browser does not support the canvas element. </canvas> <scripttype="text/javascript"> var c=document.getElementById("myCanvas"); var cxt=c.getContext("2d"); cxt.moveTo(20, 10); cxt.lineTo(150, 50); cxt.lineTo(10, 50); cxt.lineTo(20, 10); cxt.stroke(); </script>
效果如圖1-14所示。

圖1-14 三角形
另類畫圓
現(xiàn)在回到最開始的問題:如何不通過arc方法來畫一個(gè)圓形?如圖1-15所示,從正三角形到正八邊形,以此類推,正N邊形,當(dāng)N無(wú)限大時(shí),就成為一個(gè)圓形了。根據(jù)這個(gè)原理,畫出一個(gè)圓心在(150,150),半徑為100的圓形。

圖1-15 正N邊形
<canvasid="myCanvas"width="480"height="300"style="border:1px solid #c3c3c3;"> Your browser does not support the canvas element. </canvas> <scripttype="text/javascript"> var c=document.getElementById("myCanvas"); var cxt=c.getContext("2d"); var x=150; var y=150; var r=100; cxt.moveTo(x-r, y); for (var i=x-r; i < x+r+1; i++) { var tempY=Math.pow(r * r-(x-i) * (x-i), 1 / 2); cxt.lineTo(i, y+tempY); } cxt.moveTo(x-r, y); for (var i=x-r; i < x+r+1; i++) { var tempY=Math.pow(r * r-(x-i) * (x-i), 1 / 2); cxt.lineTo(i, y-tempY); } cxt.stroke(); </script>
其中用到公式:

運(yùn)行效果如圖1-16所示。

圖1-16 圓
但是,明明是在畫圓,怎么沒有看到畫圓的過程呢?JavaScript 就是這樣,解釋完就畫完了,而不會(huì)呈現(xiàn)解釋的過程,這也是為什么 JavaScript不用考慮多線程問題,僅考慮UI線程。那么如何看到畫圓的過程呢?可以使用Jscex來展示畫圓的過程。
注意:在以后的實(shí)驗(yàn)中,如果出現(xiàn)了Jscex.compile,默認(rèn)本實(shí)驗(yàn)已經(jīng)引用了Jscex庫(kù)。
<scriptsrc="jscex.min.js"type="text/javascript"></script>
這里值得注意的是,大部分實(shí)驗(yàn)都僅僅用到了Jscex的sleep,所以可以輕松改成requestAnimationFrame、settimeout、setinterval的循環(huán)方式,而不使用Jscex,復(fù)雜的線性實(shí)驗(yàn)或者深度嵌套使用Jscex是最佳選擇。
Jscex是“JavaScript Computation Expression”的縮寫,它為JavaScript語(yǔ)言提供了一個(gè)monadic擴(kuò)展。Jscex完全使用JavaScript編寫,能夠在支持ECMAScript 3的任意引擎里使用(如各瀏覽器或Node.js)。Jscex的JIT編譯器能在運(yùn)行時(shí)將JavaScript代碼編譯成Monad形式,無(wú)需額外編譯步驟,并內(nèi)置異步編程類庫(kù),可以大大簡(jiǎn)化JavaScript下的異步編程體驗(yàn)。
倘若不用Jscex,一遇到for循環(huán),就得拆算法,寫回調(diào),破壞程序的可讀性。在使用Jscex來展示畫圓的過程之前,先來看看Jscex經(jīng)常用到的一個(gè)骨架:
var somethingAsync=eval(Jscex.compile("async", function (a, b) { // implementation }));
所以下面用這種格式來使用Jscex,并且通過$await(Jscex.Async.sleep(a))使線程停住a/1000秒。
<canvasid="myCanvas"width="480"height="300"style="border: 1px solid #c3c3c3;"> Your browser does not support the canvas element. </canvas> <scriptsrc="../Scripts/jscex.min.js"type="text/javascript"></script> <scripttype="text/javascript"> var c=document.getElementById("myCanvas"); var cxt=c.getContext("2d"); var x=150; var y=150; var r=100; var drawAsync=eval(Jscex.compile("async", function () { cxt.moveTo(x-r, y); for (var i=x-r; i < x+r+1; i++) { $await(Jscex.Async.sleep(10)); \注:Sleep一會(huì)兒\ var tempY=Math.pow(r * r-(x-i) * (x-i), 1 / 2); cxt.lineTo(i, y+tempY); cxt.stroke(); } cxt.moveTo(x-r, y); for (var i=x-r; i < x+r+1; i++) { $await(Jscex.Async.sleep(10)); \注:Sleep一會(huì)兒\ var tempY=Math.pow(r * r-(x-i) * (x-i), 1 / 2); cxt.lineTo(i, y-tempY); cxt.stroke(); } })); drawAsync().start(); </script>
現(xiàn)在就可以看到畫圓的整個(gè)過程了,如圖1-17所示。

圖1-17 繪制動(dòng)畫
- 柳工出海:中國(guó)制造的全球化探索
- 24小時(shí)學(xué)會(huì)網(wǎng)站建設(shè)
- Pro/ENGINEER三維造型設(shè)計(jì)實(shí)例精解
- 小白實(shí)戰(zhàn)大前端:移動(dòng)端與前端的互通之路
- Div+CSS網(wǎng)頁(yè)制作實(shí)戰(zhàn)教程
- HTML+CSS+JavaScript網(wǎng)頁(yè)設(shè)計(jì)與布局:從新手到高手
- Photoshop網(wǎng)頁(yè)設(shè)計(jì)從入門到精通
- 社交網(wǎng)站界面設(shè)計(jì)(原書第2版)
- 電子商務(wù)網(wǎng)頁(yè)設(shè)計(jì)(第二版)
- Web開發(fā)者晉級(jí)之道:架構(gòu)、模式和領(lǐng)域驅(qū)動(dòng)設(shè)計(jì)
- 寬帶接入技術(shù)
- 秩序之美:網(wǎng)頁(yè)中的網(wǎng)格設(shè)計(jì)
- Dreamweaver CC網(wǎng)頁(yè)設(shè)計(jì)從入門到精通(微課精編版)
- Dreamweaver,F(xiàn)lash,F(xiàn)ireworks網(wǎng)頁(yè)設(shè)計(jì)百練成精(CS3版)
- After Effects UI交互動(dòng)畫設(shè)計(jì)