/**
* Copyright mutantleg ( http://wonderfl.net/user/mutantleg )
* MIT License ( http://www.opensource.org/licenses/mit-license.php )
* Downloaded from: http://wonderfl.net/c/ykA8
*/
package {
import flash.text.TextField;
import flash.events.Event;
import flash.display.Sprite;
public class FlashTest extends Sprite {
public function FlashTest() {
var a:xCutter;
var num:Number;
num = 128;
vecCutter[0].setPlane(-num, 0,0, 1, 0, 0);
vecCutter[1].setPlane(0,-num,0, 0, 1, 0);
vecCutter[2].setPlane(num, 0,0, -1, 0, 0);
vecCutter[3].setPlane(0,num,0, 0, -1, 0);
vecCutter[4].setPlane(0,0,-num, 0, 0, 1);
vecCutter[5].setPlane(0,0,num, 0, 0, -1);
deb = new TextField();
deb.mouseEnabled = false;
deb.width = 320;
deb.height = 240;
addChild(deb);
stage.addEventListener(Event.ENTER_FRAME, onEnter);
}//ctor
public var ang:Number = 0;
public var myTri:xTri = new xTri();
public var deb:TextField;
public function onEnter(e:Event):void
{
graphics.clear();
graphics.lineStyle(2, 0);
deb.text = "";
ang += 0.03;
/*
myTri.a.setValue(-200,-200,0);
myTri.b.setValue(200,0,0);
myTri.c.setValue(0,200,0);
*/
myTri.a.setValue(Math.cos(ang-1.57)*200,Math.sin(ang-1.57)*200,0);
myTri.b.setValue(Math.cos(ang)*200,Math.sin(ang)*200,0);
myTri.c.setValue(Math.cos(ang+1.57)*200,Math.sin(ang+1.57)*200,0);
//renderTri(myTri);
drawCut(myTri, 0);
}//onenter
public var vecCutter:Vector.<xCutter> = Vector.<xCutter>([new xCutter(), new xCutter(), new xCutter(), new xCutter(), new xCutter(), new xCutter()]);
public function drawCut(tri:xTri, d:int=0):void
{
var cut:xCutter;
var num:int;
if (d >= 6) { renderTri(tri); return; }
cut = vecCutter[d];
num = cut.cutTri(tri);
if (num < 0) { return; }
if (num == 0) { drawCut(tri, d+1); return; }
drawCut(cut.ret1, d+1);
if (num > 1) { drawCut(cut.ret2, d+1);}
}//drawtri
public function renderTri(tri:xTri):void
{
//deb.appendText(" tri ");
graphics.beginFill(0, 0.5);
graphics.moveTo(tri.a.cx+200, tri.a.cy+200);
graphics.lineTo(tri.b.cx+200, tri.b.cy+200);
graphics.lineTo(tri.c.cx+200, tri.c.cy+200);
graphics.lineTo(tri.a.cx+200, tri.a.cy+200);
graphics.endFill();
}//rendertri
}//classend
}
internal class xVert
{
public var cx:Number = 0;
public var cy:Number = 0;
public var cz:Number = 0;
public function copyVert(b:xVert):void { cx = b.cx; cy = b.cy; cz = b.cz; }
public function setValue(vx:Number, vy:Number, vz:Number):void
{ cx = vx; cy = vy; cz = vz;}
}//xvert
internal class xTri
{
public var a:xVert = new xVert();
public var b:xVert = new xVert();
public var c:xVert = new xVert();
}//xtri
internal class xCutter
{
public var ret1:xTri = new xTri();
public var ret2:xTri = new xTri();
public var num:int = 0;
public var cx:Number = 0;
public var cy:Number = 0;
public var cz:Number = 0;
public var cnx:Number = 0;
public var cny:Number = 0;
public var cnz:Number = 0;
public function setPlane(x_:Number, y_:Number, z_:Number, nx_:Number, ny_:Number, nz_:Number):void
{
cx = x_;
cy = y_;
cz = z_;
cnx = nx_;
cny = ny_;
cnz = nz_;
}//setplane
public function isFront(tri:xTri):int
{
var ad:Number; var bd:Number; var cd:Number;
ad = (tri.a.cx - cx) *cnx + (tri.a.cy - cy) *cny +(tri.a.cz - cz) *cnz
bd = (tri.b.cx - cx) *cnx + (tri.b.cy - cy) *cny +(tri.b.cz - cz) *cnz
cd = (tri.c.cx - cx) *cnx + (tri.c.cy - cy) *cny +(tri.c.cz - cz) *cnz
if (ad > 0 && bd > 0 && cd > 0) { return 1; } //front of plane
if (ad < 0 && bd < 0 && cd < 0) { return -1; } //behind plane
return 0; //intersect
}//isfront
public function cutTri(tri:xTri):int
{
num = cutTriPlane(tri, cx, cy,cz, cnx, cny, cnz);
return num;
}//cut
public static var tempOut:Vector.<xVert> = Vector.<xVert>([new xVert(), new xVert(), new xVert(), new xVert()]);
public function cutTriPlane(tri:xTri,
px:Number, py:Number, pz:Number,
nx:Number, ny:Number, nz:Number):int
{
var vecOut:Vector.<xVert>;
var it:int;
var i:int;
var ad:Number; var bd:Number; var cd:Number;
var t:Number;
var va:xVert; var vs:xVert;
var da:Number; var ds:Number;
var dw:xVert;
vecOut = tempOut;
ad = (tri.a.cx - px) *nx + (tri.a.cy - py) *ny +(tri.a.cz - pz) *nz
bd = (tri.b.cx - px) *nx + (tri.b.cy - py) *ny +(tri.b.cz - pz) *nz
cd = (tri.c.cx - px) *nx + (tri.c.cy - py) *ny +(tri.c.cz - pz) *nz
if (ad > 0 && bd > 0 && cd > 0) { return 0; } //front of plane
it = 0;
//todo -- unroll later (and by unroll i mean no loop really needed here)
for (i = 0; i < 3; i++)
{
if (i == 0)
{
va = tri.a; vs = tri.c; da = ad; ds = cd;
} else if (i == 1)
{
va = tri.b; vs = tri.a; da = bd; ds = ad;
} else
{
va = tri.c; vs = tri.b; da = cd; ds = bd;
}
if (da > 0 && ds > 0)
{
vecOut[it].copyVert(va);
it += 1;
}
else if (da > 0 || ds > 0)
{
t = da / (nx * (va.cx - vs.cx) + ny * (va.cy - vs.cy) + nz * (va.cz - vs.cz) );
dw = vecOut[it];
dw.cx = va.cx + (vs.cx - va.cx) * t;
dw.cy = va.cy + (vs.cy - va.cy) * t;
dw.cz = va.cz + (vs.cz - va.cz) * t;
it += 1;
if (ds < 0)
{
vecOut[it].copyVert(va);
it += 1;
}
}//endif
}//nexti
if (it < 3) { return -1;}
ret1.a.copyVert(vecOut[0]);
ret1.b.copyVert(vecOut[1]);
ret1.c.copyVert(vecOut[2]);
if (it == 3) { return 1; }
ret2.a.copyVert(vecOut[0]);
ret2.b.copyVert(vecOut[2]);
ret2.c.copyVert(vecOut[3]);
return 2;
}//cuttriplane
}//xcutter