官术网_书友最值得收藏!

實驗12 密閉球

簡介

本實驗將引入極坐標(biāo)的速度表示方式來解決物體與任意面碰撞的問題。這種方式在后面會用矢量代替。這種方式雖然可以降一個維度,二維降為一維,三維降為二維,但是這種方式無法方便地解決碰撞等物理問題,而且在使用極坐標(biāo)時描繪坐標(biāo)的位置也要相應(yīng)地改成極坐標(biāo)的形式,這樣才能體現(xiàn)其優(yōu)勢,然而Canvas的所有API都是基于X軸和Y軸的,所以后面會統(tǒng)一使用矢量計算來代替,本實驗只是拓展一下知識面。在進行實驗?zāi)M之前,先來了解幾種數(shù)學(xué)上的基本概念。

笛卡兒坐標(biāo)系

笛卡兒坐標(biāo)系是直角坐標(biāo)系和斜角坐標(biāo)系的統(tǒng)稱,如圖2-15所示。相交于原點的兩條數(shù)軸構(gòu)成了平面放射坐標(biāo)系。如兩條數(shù)軸上的度量單位相等,則稱此放射坐標(biāo)系為笛卡兒坐標(biāo)系。兩條數(shù)軸互相垂直的笛卡兒坐標(biāo)系稱為笛卡兒直角坐標(biāo)系,否則稱為笛卡兒斜角坐標(biāo)系。笛卡兒坐標(biāo)表示了點在空間中的位置,但卻和直角坐標(biāo)有區(qū)別,兩種坐標(biāo)可以相互轉(zhuǎn)換。

圖2-15 笛卡兒坐標(biāo)系

用一組數(shù)(x,y)可以表示平面上的一個點,平面上的一個點也可以用一組兩個有順序的數(shù)來表示,這就是坐標(biāo)系的雛形。

極坐標(biāo)系

在數(shù)學(xué)中,極坐標(biāo)系是一個二維坐標(biāo)系統(tǒng)。該坐標(biāo)系統(tǒng)中的點由一個夾角和一段相對于中心點——極點(相當(dāng)于較為熟知的直角坐標(biāo)系中的原點)的距離來表示,如圖2-16所示。極坐標(biāo)系的應(yīng)用領(lǐng)域十分廣泛,包括數(shù)學(xué)、物理、工程、航海及機器人領(lǐng)域。當(dāng)兩點間的關(guān)系用夾角和距離很容易表示時,極坐標(biāo)系便顯得尤為有用;而在平面直角坐標(biāo)系中,這樣的關(guān)系就只能使用三角函數(shù)來表示了。對于很多類型的曲線,極坐標(biāo)方程是最簡單的表達形式,甚至對于某些曲線來說,只有極坐標(biāo)方程能夠表示。

圖2-16 極坐標(biāo)系

極坐標(biāo)系到直角坐標(biāo)系的轉(zhuǎn)化

極坐標(biāo)系中的兩個坐標(biāo)ρθ可以由下面的公式轉(zhuǎn)換為直角坐標(biāo)系下的坐標(biāo)值:

x=ρcosθ

y=ρsinθ

由此,可得到從直角坐標(biāo)系中xy兩坐標(biāo)計算出極坐標(biāo)系下的坐標(biāo):

其中,x不等于0,在x=0的情況下,若y為正數(shù),則θ=90°(π/2 rad);若y為負數(shù),則θ=270° (3π/2 rad)。

極坐標(biāo)速度

在前幾個實驗中,使用以下方法定義小球:

        var ball={
                x: 100,
                y: 100,
                r: 15,
                vx: 100,
                vy: 100
            };

定義速度的方法是利用笛卡兒坐標(biāo)系,分別定義X軸方向的速度和Y軸方向的速度,這樣就表示了在二維坐標(biāo)系當(dāng)中的速度。利用極坐標(biāo)的方式同樣也可以定義小球的速度:

        var ball={
                x: 100,
                y: 100,
                r: 15,
                v: 100 * Math.sqrt(2),
                direction: Math.PI / 4
            };

代碼中,定義了小球的速度v和方向direction。這兩種定義方式,達到的效果是完全一樣的,vx和vy也同樣為100。

密閉球

與任意軸碰撞的實驗最適合的場景就是密閉球。圖2-17就是該實驗場景的描繪。

圖2-17 在密閉球中與任意軸碰撞的實驗

要讓運動的小球不脫離圓形范圍,所要做的就是碰撞檢測和碰撞之后小球運動方向的改變。這里假設(shè)所有碰撞是完全彈性碰撞,沒有任何速度損失。只要求出碰撞時,大圓的圓心和小球的圓心連線與水平X軸的夾角,速度方向的變化角度就迎刃而解了。

用極坐標(biāo)的形式描述速度:

        for (var i=0; i <6; i++) {
        var ball={
                      position: new Vector2(300, 250),
                      r: 10,
                      v: getRandomNumber(50, 200),
                      direction: (getRandomNumber(0, 360) / 360) * 2 * Math.PI
                  };
                  balls.push(ball);
                }

初始化一個大球:

        var bigCircularity={
                  position: new Vector2(300, 250),
                  r: 190
                }

碰撞檢測:

        if (Math.round(Math.pow(balls[i].position.x-bigCircularity.position.x, 2)+Math.pow(bigCircularity.
        position.y-balls[i].position.y, 2)) >=Math.round(Math.pow(bigCircularity.r-balls[i].r, 2))) {
        }
                // 大圓圓心到小球圓心的距離大于或等于(R-r)×(R-r)時,代表碰撞。

碰撞后,小球運動方向的改變:

        var cD=balls[i].direction;
        var step=Math.acos((balls[i].position.x-bigCircularity.posit ion.x)/
        distance);
        if (balls[i].position.y > bigCircularity.position.y) {
                balls[i].direction=-cD-Math.PI+2 * step;
              }else {
                balls[i].direction=-cD+Math.PI-2 * step;
              }

其中,step為大圓的圓心到小球的圓心這條線段與水平X軸的夾角。

運行代碼,其效果如圖2-18所示。

圖2-18 Canvas密閉球模擬

當(dāng)然,可以通過增加小球的數(shù)量,減小小球的半徑來制作很炫的粒子系統(tǒng)效果。

        for (var i=0; i < 1200; i++) {
        var ball={
                      position: new Vector2(300, 250),
                      r: 1,
                      v: getRandomNumber(50, 200),
                      direction: (getRandomNumber(0, 360) / 360) * 2 * Math.PI
                  };
                  balls.push(ball);
                }

其效果如圖2-19所示。

圖2-19 粒子系統(tǒng)模擬1

或者改變所有小球(即爆炸點)的起始位置:

        for (var i=0; i < 1200; i++) {
        var ball={
                      position: new Vector2(300, 150),
                      r: 1,
                      v: getRandomNumber(50, 200),
                      direction: (getRandomNumber(0, 360) / 360) * 2 * Math.PI
                  };
                  balls.push(ball);
                }

其效果如圖2-20所示。

圖2-20 粒子系統(tǒng)模擬2

主站蜘蛛池模板: 青川县| 高碑店市| 永新县| 晋宁县| 景洪市| 台南县| 巩留县| 石渠县| 陆良县| 无锡市| 彰化市| 揭东县| 松江区| 阿鲁科尔沁旗| 敦煌市| 长垣县| 晋州市| 阳山县| 甘孜县| 崇明县| 固始县| 丹凤县| 宁安市| 申扎县| 泰州市| 荥阳市| 富顺县| 德昌县| 古浪县| 石林| 恩平市| 沿河| 洪泽县| 长阳| 永清县| 甘南县| 临湘市| 施秉县| 冕宁县| 贵港市| 内黄县|