眾所周知,flash是一個(gè)二維的動(dòng)畫(huà)軟件,是無(wú)法完成一些真正的3d效果,但是如果要用它來(lái)做一些3d效果也不是不可能,一般來(lái)說(shuō)有以下三種方法.
第一種方法,借助其它的3d軟件,象swift 3d,Ulead Cool
3d,TrueSpace等一些相對(duì)容易上手的軟件,用它們來(lái)完成后再導(dǎo)入到flash中,效果是不錯(cuò),但是導(dǎo)入的大都是位圖系列,所以生成的文件都比較
大,再有一個(gè)特點(diǎn)就是沒(méi)有flash所特有的互動(dòng)性,作為flash 并沒(méi)有多少工作可做,它只不過(guò)是播放的工具而已.
第二種方法,理論上可以,實(shí)際上是行不通的,就是利用flash 的畫(huà)圖工具做成逐幀動(dòng)畫(huà),當(dāng)然簡(jiǎn)單的還湊合,復(fù)雜的就根本不行.
第三種方法,就是我今天所要說(shuō)的as 3d
,用數(shù)學(xué)方法算出3d來(lái),也就是利用數(shù)學(xué)公式和一些透視的知識(shí)模仿出3d效果來(lái),也稱之為假3d,是一種視覺(jué)上的錯(cuò)覺(jué).不過(guò)我個(gè)人認(rèn)為在電視上出現(xiàn)的3d
應(yīng)該都是假3d,只不過(guò)那些專業(yè)的3d軟件做出來(lái)的更逼真,更能欺騙你的眼睛罷了.
言歸正傳,我們首先認(rèn)識(shí)一下坐標(biāo)問(wèn)題,因?yàn)橐7氯S效果,必須首先了解坐標(biāo)方面的知識(shí),,因?yàn)?d效果都是三維坐標(biāo),而flash中是二維坐標(biāo),我們應(yīng)該先把三維坐標(biāo)轉(zhuǎn)換二維數(shù)學(xué)坐標(biāo),再把二維坐標(biāo)轉(zhuǎn)換為flash中的坐標(biāo),如圖:
為此我們先畫(huà)一個(gè)透視圖,B點(diǎn)是觀察者的眼睛,物體位于三維空間的A點(diǎn),它的坐標(biāo)是(x,y,z),將該點(diǎn)的坐標(biāo)轉(zhuǎn)換為二維坐標(biāo),實(shí)際上就是點(diǎn)A在平面
(電視屏幕)上的投影點(diǎn)C的坐標(biāo),其中CF的長(zhǎng)就是該點(diǎn)的X坐標(biāo)值,CE是該點(diǎn)的Y的坐標(biāo)值,假設(shè)觀察點(diǎn)到屏幕的距離BO=d,然后根據(jù)三角形相似原理,
對(duì)應(yīng)邊成比例可以得到d/(d+z)=x1/x,d/(d+z)=y1/y,其中(x1,y1)就是轉(zhuǎn)換后的坐標(biāo),假設(shè)d/(d+z)=ratio,所以
x1=x*ratio,y1=y*ratio.
這樣如果不好看懂的話,我們?cè)贀Q個(gè)角度來(lái)看,假設(shè)從上往下看和從右往左看,畫(huà)個(gè)頂視圖和右視圖,這時(shí)候頂視圖只能看到X軸和Z軸,Y軸只是一個(gè)點(diǎn),右視圖只能看到Y(jié)軸和Z軸,X而軸只是一個(gè)點(diǎn),如圖:
接下來(lái)就很簡(jiǎn)單了,二維數(shù)學(xué)坐標(biāo)和flash之間的坐標(biāo)轉(zhuǎn)換,只需把中心移動(dòng)到左上角就好了,那么A點(diǎn)最終的坐標(biāo):
_x=width/2+x1,
_y=height/2-y1,
其中width和height分別是場(chǎng)景的寬和高.
現(xiàn)在坐標(biāo)的問(wèn)題解決了,只是第一步,要想讓物體符合空間透視,還需要對(duì)其它參數(shù)做調(diào)整,比如近大遠(yuǎn)小,景深之類的,但是flash畢竟不是專門(mén)的3d軟
件,所以我們只能盡可能的模仿了,通過(guò)調(diào)整物體的比例大小,透明度和物體所處的層次可以達(dá)到比較逼真的效果,其中比例問(wèn)題的原理和坐標(biāo)相同,所以也可以根
據(jù)上面的公式得出,即:_xscale=_yscale=100*ratio(z越大,ratio就越小,離屏幕就越遠(yuǎn),物體就越小),透明度也是一樣
_alpha=100*ratio;至于層次的問(wèn)題現(xiàn)在大都用的是經(jīng)驗(yàn)值swapDepths(10000-z)或者swapDepths(-z).
導(dǎo)入三個(gè)小圖標(biāo),也可以是圖片,如果你畫(huà)的好的話,還可以畫(huà)三個(gè)小人,這樣效果更好,做成影片剪輯,拖入主場(chǎng)景中,分別命名為:mcA,mcB,mcC,然后在主場(chǎng)景的第一幀加入以下代碼:
[color=Red]mcA.x = -300;
mcA.y = 0;
mcA.z = 0;
mcA.dir = 1;//運(yùn)動(dòng)的方向
mcB.x = -50;
mcB.y = 0;
mcB.z = 250;
mcB.dir = 1;
mcC.x = 200;
mcC.y = 0;
mcC.z = 500;
mcC.dir = 1;//以上為三個(gè)圖標(biāo)的三維坐標(biāo)值
d = 300;
speed = 20;
mcMove = function () {
this.z += speed*this.dir;
if (this.z>500) {
this.z = 500;
this.dir = -1;
} else if (this.z<0) {
this.z = 0;
this.dir = 1;
}
var ratio = d/(d+this.z);
this._x = 250+this.x*ratio;
this._y = 150-this.y*ratio;//將三維坐標(biāo)轉(zhuǎn)化為二維坐標(biāo)
this._xscale = this._yscale=100*ratio;
this.swapDepths(-this.z);//調(diào)整比例大小,透明度和層次讓它符合透視原理
};
mcA.onEnterFrame = mcMove;
mcB.onEnterFrame = mcMove;
mcC.onEnterFrame = mcMove; [/color]
這里是swf文件:3d1.swf
附件: 3d1.swf
接下來(lái)我們?cè)僮鲆粋€(gè)例子,在這個(gè)例子里我們引入一個(gè)鏡頭的概念,通過(guò)改變鏡頭的遠(yuǎn)近來(lái)實(shí)現(xiàn)一些更酷的效果,在主場(chǎng)景的第一幀加入以下代碼:
[color=Red]this.createEmptyMovieClip("scene", 1);
scene._x = scene._y=200;/
scene.depth = 1;//建立一個(gè)空的影片剪輯,用來(lái)包含一切的3d元素
cameraView = new Object();
cameraView.x = 0;
cameraView.y = 0;
cameraView.z = 0;//鏡頭坐標(biāo)的初始值
cameraView.target = new Object();
cameraView.target.x = 0;
cameraView.target.y = 0;
cameraView.target.z = 0;//目標(biāo)鏡頭的坐標(biāo)值
d = 200;//眼睛和屏幕的距離
selectPic = function () {
cameraView.target.x = this.x;
cameraView.target.y = this.y;
cameraView.target.z = this.z;
};//這個(gè)函數(shù)就是每選擇一個(gè)圖時(shí),把這個(gè)圖的坐標(biāo)作為目標(biāo)鏡頭的坐標(biāo)
displayPic = function (cameraView, d) {
var x = this.x-cameraView.x;
var y = this.y-cameraView.y;
var z = this.z-cameraView.z;
if (z<0) {
this.z += 5000;
this.x = 1000-Math.random()*1000;
this.y = 1000-Math.random()*1000;
x = this.x-cameraView.x;
y = this.y-cameraView.y;
z = this.z-cameraView.z;
}
var ratio = d/(d+z);
this._x = x*ratio;
this._y = y*ratio;
this._xscale = this._yscale=100*ratio;
this.swapDepths(1000-z);
};
Pic = new Array();
for (var i = 1; i<=10; i++) {
mc = scene.attachMovie("pic"+i, "pic"+i, scene.depth++);//導(dǎo)入10個(gè)圖標(biāo),做成影片剪輯
mc.x = 1000-Math.random()*1000;
mc.y = 1000-Math.random()*1000;
mc.z = i*500;
mc.onRelease = selectPic;
mc.display = displayPic;
Pic.push(mc);
}
scene.onEnterFrame = function() {
cameraView.x += (cameraView.target.x-cameraView.x)/5;
cameraView.y += (cameraView.target.y-cameraView.y)/5;
cameraView.z += (cameraView.target.z-cameraView.z)/5;//緩沖公式
for (var i = 0; i<=Pic.length; i++) {
Pic.display(cameraView, d);
}
}; [/color]
這里是swf文件:3d2.swf ,接下來(lái)的這倆個(gè)例子,都是利用了鏡頭的概念,你可以利用鍵盤(pán)的方向鍵來(lái)控制看看效果。
以上的例子雖然有了點(diǎn)3d的效果了,但是都是直來(lái)直去,并沒(méi)有涉及到旋轉(zhuǎn)的效果,那么接下來(lái)我們?cè)僦v一下物體在三維空間里的旋轉(zhuǎn)效果是如何制作的,.我們把旋轉(zhuǎn)分成三種情況來(lái)講,繞X軸,繞Y軸,繞Z軸旋轉(zhuǎn),首先講一下繞X軸旋轉(zhuǎn),如圖:
點(diǎn)A繞X軸旋轉(zhuǎn)b到達(dá)點(diǎn)B,X坐標(biāo)的值是不變的,即x1=x,OA=OB=r,再這里首先要說(shuō)兩個(gè)數(shù)學(xué)里三角函數(shù)的公式:
sina=對(duì)邊/斜邊,
cosa=鄰邊/斜邊,.
sin(a+b)=sina*cosb+cosa*sinb,
cos(a+b)=cosa*cosb-sina*sinb,
所以點(diǎn)A的坐標(biāo):
y=r*sina,
z=r*cosa,
旋轉(zhuǎn)后B點(diǎn)的坐標(biāo):
y1=r*sin(a+b),
z1=r*cos(a+b),
最后得到旋轉(zhuǎn)后B點(diǎn)的坐標(biāo)與旋轉(zhuǎn)前A點(diǎn)坐標(biāo)的關(guān)系:
y1=y*cosb+z*sinb,
z1=z*cosb-y*sinb,
這個(gè)公式很重要,在3d效果里涉及到旋轉(zhuǎn)都要用到這個(gè)公式,
同樣我們還可以計(jì)算出饒Y軸旋轉(zhuǎn)的公式:
x1=x*cosb+z*sinb,
z1=z*cosb-x*sinb,
繞Z軸旋轉(zhuǎn)的公式:
x1=x*cosb+y*sinb,
y1=y*cosb-x*sinb,
有了以上的知識(shí),我們就可以做一個(gè)空間旋轉(zhuǎn)的例子,在主場(chǎng)景加入以下代碼:

[color=Red] this.createEmptyMovieClip("Scene", 1);
Scene._x = 150;
Scene._y = 150;
d = 300;//眼睛和屏幕之間的距離,試著調(diào)整看有什么變化
make3DPoint = function(x,y,z){
var point = new Object();
point.x = x;
point.y = y;
point.z = z;
return point;
};
make2DPoint = function(x, y, depth, ratio){
var point = new Object();
point.x = x;
point.y = y;
point.depth = depth;
point.ratio = ratio;
return point;
};
Transform3DPointsTo2DPoints = function(points, rotations){
var myArray = [];
var sx = Math.sin(rotations.x);
var cx = Math.cos(rotations.x);
var sy = Math.sin(rotations.y);
var cy = Math.cos(rotations.y);
var sz = Math.sin(rotations.z);
var cz = Math.cos(rotations.z);
var x,y,z, xy,xz, yx,yz, zx,zy, ratio;
var i = points.length;
while (i--){
x = points.x;
y = points.y;
z = points.z;
xy = cx*y - sx*z;
xz = sx*y + cx*z;
yz = cy*xz - sy*x;
yx = sy*xz + cy*x;
zx = cz*yx - sz*xy;
zy = sz*yx + cz*xy;//旋轉(zhuǎn)后的坐標(biāo)值
ratio = d/(d + yz);
x = zx*ratio;
y = zy*ratio;//再轉(zhuǎn)化為二維坐標(biāo)
z = yz;
myArray = make2DPoint(x, y, -z, ratio);
}
return myArray;
};//以上三個(gè)函數(shù)很重要,因?yàn)樵诖蠖鄶?shù)3d效果的例子里都能用到,可以說(shuō)是公式了,尤其是最后一個(gè)
pointsArray = [
make3DPoint(-50,-50,-50),
make3DPoint(50,-50,-50),
make3DPoint(50,-50,50),
make3DPoint(-50,-50,50),
make3DPoint(-50,50,-50),
make3DPoint(50,50,-50),
make3DPoint(50,50,50),
make3DPoint(-50,50,50)
];//正方體四個(gè)頂點(diǎn)的坐標(biāo)
for (i=0; i<pointsArray.length; i++){
attachedObj =Scene.attachMovie("ball", "ball"+i, i);
}//畫(huà)一個(gè)小球,轉(zhuǎn)化為影片剪輯
myRotations = make3DPoint(0,0,0);
Scene.onEnterFrame = function(){
myRotations.y -= this._xmouse/2000;
myRotations.x += this._ymouse/2000;//鼠標(biāo)互動(dòng),你也可以調(diào)整2000這個(gè)值讓它轉(zhuǎn)的更快或者更慢,也可以換成固定值
var screenPoints = Transform3DPointsTo2DPoints(pointsArray, myRotations);
for (i=0; i<pointsArray.length; i++){
myball = this["ball"+i];
myball._x = screenPoints.x;
myball._y = screenPoints.y;
myball._xscale = myball._yscale = 100 * screenPoints.ratio;
myball.swapDepths(screenPoints.depth);
}
};[/color]
按Ctrl+Enter效果就出來(lái)了,是不是很酷啊?
這是swf文件:3d3.swf
當(dāng)然我們可以再加點(diǎn)東西,在剛才的onEnterFrame事件后再加以下代碼看看又會(huì)如何:
[color=Red]this.clear();
this.lineStyle(2, 0xff0000, 100);
// 頂面的四條線
this.moveTo(screenPoints[0].x, screenPoints[0].y);
this.lineTo(screenPoints[1].x, screenPoints[1].y);
this.lineTo(screenPoints[2].x, screenPoints[2].y);
this.lineTo(screenPoints[3].x, screenPoints[3].y);
this.lineTo(screenPoints[0].x, screenPoints[0].y);
// 底面的四條線
this.moveTo(screenPoints[4].x, screenPoints[4].y);
this.lineTo(screenPoints[5].x, screenPoints[5].y);
this.lineTo(screenPoints[6].x, screenPoints[6].y);
this.lineTo(screenPoints[7].x, screenPoints[7].y);
this.lineTo(screenPoints[4].x, screenPoints[4].y);
// 把頂面和第面用四條線連起來(lái)
this.moveTo(screenPoints[0].x, screenPoints[0].y);
this.lineTo(screenPoints[4].x, screenPoints[4].y);
this.moveTo(screenPoints[1].x, screenPoints[1].y);
this.lineTo(screenPoints[5].x, screenPoints[5].y);
this.moveTo(screenPoints[2].x, screenPoints[2].y);
this.lineTo(screenPoints[6].x, screenPoints[6].y);
this.moveTo(screenPoints[3].x, screenPoints[3].y);
this.lineTo(screenPoints[7].x, screenPoints[7].y);
//以上代碼是一個(gè)簡(jiǎn)單的畫(huà)圖程序 [/color]
再加點(diǎn)東西,在上面的畫(huà)圖程序里加上以下倆句看有什么:
[color=Red]this.beginFill(0x00ff00,80);
this.endFill(); [/color]
這是swf文件:3d3B.swf "3d3C.swf
從上面的例子里我們把a(bǔ)s畫(huà)圖和3d效果結(jié)合起來(lái),那么我們接下來(lái)就專門(mén)講一下這方面的例子,用純粹的as 做一些3d效果,先畫(huà)一個(gè)旋轉(zhuǎn)的正方形,在第一幀加入以下的代碼:
[code][/code]
this.createEmptyMovieClip("theScene", 1);
theScene._x = 150;
theScene._y = 150;
d = 300;
make3DPoint = function(x,y,z){
var point = new Object();
point.x = x;
point.y = y;
point.z = z;
return point;
};
make2DPoint = function(x, y){
var point = new Object();
point.x = x;
point.y = y;
return point;
};
Transform3DPointsTo2DPoints = function(points,rotations){
var myArray = [];
var sx = Math.sin( rotations.x);
var cx = Math.cos( rotations.x);
var sy = Math.sin( rotations.y);
var cy = Math.cos( rotations.y);
var sz = Math.sin( rotations.z);
var cz = Math.cos( rotations.z);
var x,y,z, xy,xz, yx,yz, zx,zy, ratio;
var i = points.length;
while (i--){
x = points.x;
y = points.y;
z = points.z;
xy = cx*y - sx*z;
xz = sx*y + cx*z;
yz = cy*xz - sy*x;
yx = sy*xz + cy*x;
zx = cz*yx - sz*xy;
zy = sz*yx + cz*xy;
ratio = d/(d + yz);
x = zx*ratio;
y = zy*ratio;
myArray = make2DPoint(x, y);
}
return myArray;
};
pointsArray = [
make3DPoint(-50,-50,-50),
make3DPoint(50,-50,-50),
make3DPoint(50,-50,50),
make3DPoint(-50,-50,50),
make3DPoint(-50,50,-50),
make3DPoint(50,50,-50),
make3DPoint(50,50,50),
make3DPoint(-50,50,50)
];
myRotations = make3DPoint(0,0,0);
theScene.onEnterFrame = function(){
myRotations.y -= this._xmouse/3000;
myRotations.x += this._ymouse/3000;
var screenPoints = Transform3DPointsTo2DPoints(pointsArray, myRotations);
this.clear();
this.lineStyle(2,0xff0000,100);
// top
this.moveTo(screenPoints[0].x, screenPoints[0].y);
this.lineTo(screenPoints[1].x, screenPoints[1].y);
this.lineTo(screenPoints[2].x, screenPoints[2].y);
this.lineTo(screenPoints[3].x, screenPoints[3].y);
this.lineTo(screenPoints[0].x, screenPoints[0].y);
// bottom
this.moveTo(screenPoints[4].x, screenPoints[4].y);
this.lineTo(screenPoints[5].x, screenPoints[5].y);
this.lineTo(screenPoints[6].x, screenPoints[6].y);
this.lineTo(screenPoints[7].x, screenPoints[7].y);
this.lineTo(screenPoints[4].x, screenPoints[4].y);
// connecting bottom and top
this.moveTo(screenPoints[0].x, screenPoints[0].y);
this.lineTo(screenPoints[4].x, screenPoints[4].y);
this.moveTo(screenPoints[1].x, screenPoints[1].y);
this.lineTo(screenPoints[5].x, screenPoints[5].y);
this.moveTo(screenPoints[2].x, screenPoints[2].y);
this.lineTo(screenPoints[6].x, screenPoints[6].y);
this.moveTo(screenPoints[3].x, screenPoints[3].y);
this.lineTo(screenPoints[7].x, screenPoints[7].y);
};
這是swf文件:3d4.swf
看看這段程序和上面的程序是不是很相似,其實(shí)只要你掌握了其中的原理,只需要把里面的東西作一些相應(yīng)的變換就可以做成你自己想的很酷的效果,現(xiàn)在我再把上
面的程序稍做調(diào)整,原碼我就不寫(xiě)了,你可以自己考慮一下.上面做的都是正方形,如果把坐標(biāo)做相應(yīng)的調(diào)整,還可以做成其它立體圖形,比如三角形,五角形等,
關(guān)于單純的由線條組成的立體圖形現(xiàn)在看來(lái)很簡(jiǎn)單,只要你知道各個(gè)點(diǎn)的坐標(biāo)就可以用以上的方法做出來(lái),當(dāng)然你還可以把它填充起來(lái),比如上面的那個(gè)正方體.現(xiàn)
在我就利用beginFill()和endFill()這倆個(gè)方法在上面的基礎(chǔ)把這個(gè)立方體填充起來(lái).把上面的立方體去掉線條,只留下三個(gè)面,又是另一個(gè)
效果:這是swf文件:3d4B.swf " 3d4C.swf
當(dāng)然你也可以利用以上的知識(shí)自己做一些很酷的效果,只需要將上面的坐標(biāo)坐標(biāo)變換一下就能做出很多圖形,下面是我做的一個(gè)平面五角星和一個(gè)只有線條的立體五角星,因?yàn)樽鴺?biāo)是我自己用苯辦法算出里的,所以有點(diǎn)不大像.
下面這個(gè)立體圖形的坐標(biāo)我給出來(lái)看大家能不能自己做出來(lái).
v1(15.9689,-22.1275,-0.135825),
v2(-15.3241,-22.1275,-0.135825),
v3(15.9689,1.32056e-006,21.9917),
v4(-15.3241,1.32255e-006,21.9917),
v5(-15.3241,-1.31526e-006,-22.2633),
v6(15.9686,-1.31725e-006,-22.2633),
v7(15.9686,22.1275,-0.135827),
v8(-15.3241,22.1275,-0.135827),
v9(0.322368,-84.0845,83.9487),
v10(0.322369,-84.0845,-84.2204),
v11(119.236,0.0,-0.135826),
v12(0.322368,84.0845,-84.2204),
v13(0.322386,84.0845,83.9487),
v14(-118.591,0,-0.135826)
一共有十四個(gè)點(diǎn),組成二十四個(gè)面,下面是每個(gè)面對(duì)應(yīng)的那幾個(gè)點(diǎn):
fa1=9,fb1=1,fc1=3,fa2=9,fb2=3,fc2=4,fa3=9,fb3=4,fc3=2,fa4=9,fb4=2,fc4=1,fa5=10,fb5=2,fc5=5,
fa6=10,fb6=5,fc6=6,fa7=10,fb7=6,fc7=1,fa8=10,fb8=1,fc8=2,fa9=11,fb9=6,fc9=7,fa10=11,fb10=7,fc10=3,
fa11=11,fb11=3,fc11=1,fa12=11,fb12=1,fc12=6,fa13=12,fb13=6,fc13=5,fa14=12,fb14=5,fc14=8,
fa15=12,fb15=8,fc15=7,fa16=12,fb16=7,fc16=6,fa17=13,fb17=8,fc17=4,fa18=13,fb18=4,fc18=3,
fa19=13,fb19=3,fc19=7,fa20=13,fb20=7,fc20=8,fa21=14,fb21=8,fc21=5,fa22=14,fb22=5,fc22=2,
fa23=14,fb23=2,fc23=4,fa24=14,fb24=4,fc24=8
這是我做的幾個(gè)例子:swf文件:3d10.swf "3d10B.swf "3d10C.swf
做旋轉(zhuǎn)的六面體還有另一種做法,前面的那中方法,做出來(lái)的實(shí)際并不逼真,下面先看看我用另一個(gè)方法做出來(lái)的例子看與這個(gè)有什么區(qū)別呢,代碼如下:
[color=Red] this.createEmptyMovieClip("theScene", 1);
theScene._x = 150;
theScene._y = 150;
d = 300;
make3DPoint = function(x,y,z){
var point = new Object();
point.x = x;
point.y = y;
point.z = z;
return point;
};
make2DPoint = function(x,y){
var point = new Object();
point.x = x;
point.y = y;
return point;
};
isVisibleBetween = function(a,b,c){
if (((b.y-a.y)/(b.x-a.x)-(c.y-a.y)/(c.x-a.x)<0)^(a.x<=b.x == a.x>c.x)){
return true;
}else{
return false;
}
};[/color]
//
這個(gè)函數(shù)很重要,你不必知道它的原理,只要知道怎么用就可以了,其實(shí)我也不知道怎么解釋它,但是這個(gè)函數(shù)可以根據(jù)一個(gè)平面上任意三個(gè)點(diǎn)的坐標(biāo)而判斷該平面
是否看的見(jiàn),因?yàn)橐粋€(gè)立體圖形在平面上最多可以顯示三個(gè)面,所以就必須判斷你可以看的那三個(gè)面,這個(gè)函數(shù)不僅可以用在四面體上,不管有多少面的立體圖形都
可以用這個(gè)公式:
[color=Red] drawFilledSquare = function(a,b,c,d){
this.clear();
this.lineStyle(2,0,100);
if (isVisibleBetween(a,b,c)){
this.moveTo(a.x, a.y);
this.beginFill(this.col, 100);
this.lineTo(b.x, b.y);
this.lineTo(c.x, c.y);
this.lineTo(d.x, d.y);
this.lineTo(a.x, a.y);
this.endFill();
}
};[/color]
//這里就是上面函數(shù)的應(yīng)用,如果這個(gè)面看的見(jiàn)就畫(huà)出它,
//下面的程序基本上就成為了一種固定的形式了:
[color=Red]Transform3DPointsTo2DPoints = function(points, axisRotations){
var myArray = [];
var sx = Math.sin(axisRotations.x);
var cx = Math.cos(axisRotations.x);
var sy = Math.sin(axisRotations.y);
var cy = Math.cos(axisRotations.y);
var sz = Math.sin(axisRotations.z);
var cz = Math.cos(axisRotations.z);
var x,y,z, xy,xz, yx,yz, zx,zy, scaleRatio;
var i = points.length;
while (i--){
x = points.x;
y = points.y;
z = points.z;
xy = cx*y - sx*z;
xz = sx*y + cx*z;
yz = cy*xz - sy*x;
yx = sy*xz + cy*x;
zx = cz*yx - sz*xy;
zy = sz*yx + cz*xy;
scaleRatio = d/(d + yz);
x = zx*scaleRatio;
y = zy*scaleRatio;
myArray = make2DPoint(x, y);
}
return myArray;
};
pointsArray = [
make3DPoint(-50,-50,-50),
make3DPoint(50,-50,-50),
make3DPoint(50,-50,50),
make3DPoint(-50,-50,50),
make3DPoint(-50,50,-50),
make3DPoint(50,50,-50),
make3DPoint(50,50,50),
make3DPoint(-50,50,50)
];
rollOverFace = function(){
this.col = 0xff0000;
};
rollOutFace = function(){
this.col = 0xdddddd;
};
for (i=0; i<6; i++){
emptyFace = theScene.createEmptyMovieClip("face"+i,i);
emptyFace.col = 0xdddddd;
emptyFace.onRollOver = emptyFace.onDragOver = rollOverFace;
emptyFace.onRollOut = emptyFace.onDragOut = rollOutFace;
emptyFace.onPress = pressFace;
emptyFace.draw = drawFilledSquare;
}
cubeAxisRotations = make3DPoint(0,0,0);
theScene.onEnterFrame = function(){
cubeAxisRotations.y -= this._xmouse/3000;
cubeAxisRotations.x += this._ymouse/3000;
var pts2D = Transform3DPointsTo2DPoints(pointsArray, cubeAxisRotations);
this.face0.draw(pts2D[0], pts2D[3], pts2D[2], pts2D[1]);
this.face1.draw(pts2D[4], pts2D[5], pts2D[6], pts2D[7]);
this.face2.draw(pts2D[0], pts2D[4], pts2D[7], pts2D[3]);
this.face3.draw(pts2D[3], pts2D[7], pts2D[6], pts2D[2]);
this.face4.draw(pts2D[2], pts2D[6], pts2D[5], pts2D[1]);
this.face5.draw(pts2D[1], pts2D[5], pts2D[4], pts2D[0]);
}; [/color]
這是swf文件:3d5.swf
現(xiàn)在我們?cè)侔焉厦娴淖鴺?biāo)換成三角形的坐標(biāo),再把最后畫(huà)圖的部分也做一下調(diào)整,那么就很容易做成一個(gè)旋轉(zhuǎn)的的四面體了,具體調(diào)整如下:
[color=Red] pointsArray = [
make3DPoint(-50,87,29),
make3DPoint(0,87,-58),
make3DPoint(50,87,29),
make3DPoint(0,0,0)
];//這是坐標(biāo)部分
this.face0.draw(pts2D[0], pts2D[1], pts2D[2]);
this.face1.draw(pts2D[0], pts2D[3], pts2D[1]);
this.face2.draw(pts2D[1], pts2D[3], pts2D[2]);
this.face3.draw(pts2D[2], pts2D[3], pts2D[0]);
//這是畫(huà)圖部分[/color]
這是swf文件:3d6.swf .下面的幾個(gè)例子也是在此基礎(chǔ)上擴(kuò)展的:3d6C.swf ;最后來(lái)個(gè)超酷的飛機(jī),這可是純AS做的哦:3d7B.swf .
上面的例子比較常見(jiàn),當(dāng)然還有一些其它的效果,我現(xiàn)在再給大家連出一些這方面的例子:
有投影的三維效果:3DB2.swf " 3DF.swf
有彈性的立體小球:3DD.swf
可以拖動(dòng)的小球:3DA.swf
最后是我做的兩個(gè),一個(gè)是可以用鍵盤(pán)方向鍵控制旋轉(zhuǎn)的立體DNA,另一個(gè)是我用BitmapData類做的空間旋轉(zhuǎn)的立方體. DNA_exam2.swf "3d9.swf