starling-framework
Version:
A fast, productive library for 2D cross-platform development.
365 lines (350 loc) • 12.5 kB
JavaScript
// Class: starling.geom.Polygon
var $global = typeof window != "undefined" ? window : typeof global != "undefined" ? global : typeof self != "undefined" ? self : this
$global.Object.defineProperty(exports, "__esModule", {value: true});
var __map_reserved = {};
// Imports
var $hxClasses = require("./../../hxClasses_stub").default;
var $hxEnums = require("./../../hxEnums_stub").default;
var $import = require("./../../import_stub").default;
function openfl__$Vector_Vector_$Impl_$() {return require("./../../openfl/_Vector/Vector_Impl_");}
function Std() {return require("./../../Std");}
function openfl_geom_Point() {return $import(require("openfl/geom/Point"));}
function js_Boot() {return require("./../../js/Boot");}
function js__$Boot_HaxeError() {return require("./../../js/_Boot/HaxeError");}
function openfl_errors_ArgumentError() {return $import(require("openfl/errors/ArgumentError"));}
function Type() {return require("./../../Type");}
function openfl_errors_RangeError() {return $import(require("openfl/errors/RangeError"));}
function starling_rendering_IndexData() {return require("./../../starling/rendering/IndexData");}
function starling_utils_Pool() {return require("./../../starling/utils/Pool");}
function starling_utils_MathUtil() {return require("./../../starling/utils/MathUtil");}
function starling_geom_Ellipse() {return require("./../../starling/geom/Ellipse");}
function starling_geom_Rectangle() {return require("./../../starling/geom/Rectangle");}
// Constructor
var Polygon = function(vertices) {
this.__coords = (openfl__$Vector_Vector_$Impl_$().default)._new();
this.addVertices(vertices);
}
// Meta
Polygon.__name__ = "starling.geom.Polygon";
Polygon.__isInterface__ = false;
Polygon.prototype = {
clone: function() {
var clone = new Polygon();
var numCoords = this.__coords.length;
var _g = 0;
var _g1 = numCoords;
while(_g < _g1) {
var i = _g++;
(openfl__$Vector_Vector_$Impl_$().default).set(clone.__coords,i,this.__coords[i]);
}
return clone;
},
reverse: function() {
var numCoords = this.__coords.length;
var numVertices = (Std().default).int(numCoords / 2);
var tmp;
var i = 0;
while(i < numVertices) {
tmp = this.__coords[i];
(openfl__$Vector_Vector_$Impl_$().default).set(this.__coords,i,this.__coords[numCoords - i - 2]);
(openfl__$Vector_Vector_$Impl_$().default).set(this.__coords,numCoords - i - 2,tmp);
tmp = this.__coords[i + 1];
(openfl__$Vector_Vector_$Impl_$().default).set(this.__coords,i + 1,this.__coords[numCoords - i - 1]);
(openfl__$Vector_Vector_$Impl_$().default).set(this.__coords,numCoords - i - 1,tmp);
i += 2;
}
},
addVertices: function(args) {
var i;
var numArgs = args != null ? args.length : 0;
var numCoords = this.__coords.length;
if(numArgs > 0) {
if(((args[0]) instanceof (openfl_geom_Point().default))) {
var _g = 0;
var _g1 = numArgs;
while(_g < _g1) {
var i1 = _g++;
(openfl__$Vector_Vector_$Impl_$().default).set(this.__coords,numCoords + i1 * 2,((js_Boot().default).__cast(args[i1] , (openfl_geom_Point().default))).x);
(openfl__$Vector_Vector_$Impl_$().default).set(this.__coords,numCoords + i1 * 2 + 1,((js_Boot().default).__cast(args[i1] , (openfl_geom_Point().default))).y);
}
} else if(typeof(args[0]) == "number") {
var _g2 = 0;
var _g11 = numArgs;
while(_g2 < _g11) {
var i2 = _g2++;
(openfl__$Vector_Vector_$Impl_$().default).set(this.__coords,numCoords + i2,args[i2]);
}
} else {
throw new (js__$Boot_HaxeError().default)(new (openfl_errors_ArgumentError().default)("Invalid type: " + (Type().default).getClassName((Type().default).getClass(args[0]))));
}
}
},
setVertex: function(index,x,y) {
if(index >= 0 && index <= this.get_numVertices()) {
(openfl__$Vector_Vector_$Impl_$().default).set(this.__coords,index * 2,x);
(openfl__$Vector_Vector_$Impl_$().default).set(this.__coords,index * 2 + 1,y);
} else {
throw new (js__$Boot_HaxeError().default)(new (openfl_errors_RangeError().default)("Invalid index: " + index));
}
},
getVertex: function(index,out) {
if(index >= 0 && index < this.get_numVertices()) {
out = out == null ? new (openfl_geom_Point().default)() : out;
out.setTo(this.__coords[index * 2],this.__coords[index * 2 + 1]);
return out;
} else {
throw new (js__$Boot_HaxeError().default)(new (openfl_errors_RangeError().default)("Invalid index: " + index));
}
},
contains: function(x,y) {
var numVertices = this.get_numVertices();
var i;
var j = numVertices - 1;
var oddNodes = 0;
var _g = 0;
var _g1 = numVertices;
while(_g < _g1) {
var i1 = _g++;
var ix = this.__coords[i1 * 2];
var iy = this.__coords[i1 * 2 + 1];
var jx = this.__coords[j * 2];
var jy = this.__coords[j * 2 + 1];
if((iy < y && jy >= y || jy < y && iy >= y) && (ix <= x || jx <= x)) {
oddNodes = oddNodes ^ (ix + (y - iy) / (jy - iy) * (jx - ix) < x ? 1 : 0);
}
j = i1;
}
return oddNodes != 0;
},
containsPoint: function(point) {
return this.contains(point.x,point.y);
},
triangulate: function(indexData,offset) {
if(offset == null) {
offset = 0;
}
var numVertices = this.get_numVertices();
var numTriangles = this.get_numTriangles();
var i;
if(indexData == null) {
indexData = new (starling_rendering_IndexData().default)(numTriangles * 3);
}
if(numTriangles == 0) {
return indexData;
}
Polygon.sRestIndices.length = numVertices;
var _g = 0;
var _g1 = numVertices;
while(_g < _g1) {
var i1 = _g++;
(openfl__$Vector_Vector_$Impl_$().default).set(Polygon.sRestIndices,i1,i1);
}
var restIndexPos = 0;
var numRestIndices = numVertices;
var a = (starling_utils_Pool().default).getPoint();
var b = (starling_utils_Pool().default).getPoint();
var c = (starling_utils_Pool().default).getPoint();
var p = (starling_utils_Pool().default).getPoint();
while(numRestIndices > 3) {
var otherIndex;
var earFound = false;
var i0 = Polygon.sRestIndices[restIndexPos % numRestIndices];
var i11 = Polygon.sRestIndices[(restIndexPos + 1) % numRestIndices];
var i2 = Polygon.sRestIndices[(restIndexPos + 2) % numRestIndices];
a.setTo(this.__coords[2 * i0],this.__coords[2 * i0 + 1]);
b.setTo(this.__coords[2 * i11],this.__coords[2 * i11 + 1]);
c.setTo(this.__coords[2 * i2],this.__coords[2 * i2 + 1]);
if(Polygon.isConvexTriangle(a.x,a.y,b.x,b.y,c.x,c.y)) {
earFound = true;
var _g2 = 3;
var _g3 = numRestIndices;
while(_g2 < _g3) {
var i3 = _g2++;
otherIndex = Polygon.sRestIndices[(restIndexPos + i3) % numRestIndices];
p.setTo(this.__coords[2 * otherIndex],this.__coords[2 * otherIndex + 1]);
if((starling_utils_MathUtil().default).isPointInTriangle(p,a,b,c)) {
earFound = false;
break;
}
}
}
if(earFound) {
indexData.addTriangle(i0 + offset,i11 + offset,i2 + offset);
(openfl__$Vector_Vector_$Impl_$().default).removeAt(Polygon.sRestIndices,(restIndexPos + 1) % numRestIndices);
--numRestIndices;
restIndexPos = 0;
} else {
++restIndexPos;
if(restIndexPos == numRestIndices) {
break;
}
}
}
(starling_utils_Pool().default).putPoint(a);
(starling_utils_Pool().default).putPoint(b);
(starling_utils_Pool().default).putPoint(c);
(starling_utils_Pool().default).putPoint(p);
indexData.addTriangle(Polygon.sRestIndices[0] + offset,Polygon.sRestIndices[1] + offset,Polygon.sRestIndices[2] + offset);
return indexData;
},
copyToVertexData: function(target,targetVertexID,attrName) {
if(attrName == null) {
attrName = "position";
}
if(targetVertexID == null) {
targetVertexID = 0;
}
var numVertices = this.get_numVertices();
var requiredTargetLength = targetVertexID + numVertices;
if(target.get_numVertices() < requiredTargetLength) {
target.set_numVertices(requiredTargetLength);
}
var _g = 0;
var _g1 = numVertices;
while(_g < _g1) {
var i = _g++;
target.setPoint(targetVertexID + i,attrName,this.__coords[i * 2],this.__coords[i * 2 + 1]);
}
},
toString: function() {
var result = "[Polygon";
var numPoints = this.get_numVertices();
if(numPoints > 0) {
result += "\n";
}
var _g = 0;
var _g1 = numPoints;
while(_g < _g1) {
var i = _g++;
result += " [Vertex " + i + ": " + "x=" + (starling_utils_MathUtil().default).toFixed(this.__coords[i * 2],1) + ", " + "y=" + (starling_utils_MathUtil().default).toFixed(this.__coords[i * 2 + 1],1) + "]" + (i == numPoints - 1 ? "\n" : ",\n");
}
return result + "]";
},
get_isSimple: function() {
var numCoords = this.__coords.length;
if(numCoords <= 6) {
return true;
}
var i = 0;
while(i < numCoords) {
var ax = this.__coords[i];
var ay = this.__coords[i + 1];
var bx = this.__coords[(i + 2) % numCoords];
var by = this.__coords[(i + 3) % numCoords];
var endJ = i + numCoords - 2;
var j = i + 4;
while(j < endJ) {
var cx = this.__coords[j % numCoords];
var cy = this.__coords[(j + 1) % numCoords];
var dx = this.__coords[(j + 2) % numCoords];
var dy = this.__coords[(j + 3) % numCoords];
if(Polygon.areVectorsIntersecting(ax,ay,bx,by,cx,cy,dx,dy)) {
return false;
}
j += 2;
}
i += 2;
}
return true;
},
get_isConvex: function() {
var numCoords = this.__coords.length;
if(numCoords < 6) {
return true;
} else {
var i = 0;
while(i < numCoords) {
if(!Polygon.isConvexTriangle(this.__coords[i],this.__coords[i + 1],this.__coords[(i + 2) % numCoords],this.__coords[(i + 3) % numCoords],this.__coords[(i + 4) % numCoords],this.__coords[(i + 5) % numCoords])) {
return false;
}
i += 2;
}
}
return true;
},
get_area: function() {
var area = 0;
var numCoords = this.__coords.length;
if(numCoords >= 6) {
var i = 0;
while(i < numCoords) {
area += this.__coords[i] * this.__coords[(i + 3) % numCoords];
area -= this.__coords[i + 1] * this.__coords[(i + 2) % numCoords];
i += 2;
}
}
return area / 2.0;
},
get_numVertices: function() {
return (Std().default).int(this.__coords.length / 2);
},
set_numVertices: function(value) {
var oldLength = this.get_numVertices();
this.__coords.length = value * 2;
if(oldLength < value) {
var _g = oldLength;
var _g1 = value;
while(_g < _g1) {
var i = _g++;
(openfl__$Vector_Vector_$Impl_$().default).set(this.__coords,i * 2,(openfl__$Vector_Vector_$Impl_$().default).set(this.__coords,i * 2 + 1,0.0));
}
}
return value;
},
get_numTriangles: function() {
var numVertices = this.get_numVertices();
if(numVertices >= 3) {
return numVertices - 2;
} else {
return 0;
}
}
};
Polygon.prototype.__class__ = Polygon.prototype.constructor = $hxClasses["starling.geom.Polygon"] = Polygon;
// Init
Object.defineProperties(Polygon.prototype,{ isSimple : { get : function () { return this.get_isSimple (); }}, isConvex : { get : function () { return this.get_isConvex (); }}, area : { get : function () { return this.get_area (); }}, numVertices : { get : function () { return this.get_numVertices (); }, set : function (v) { return this.set_numVertices (v); }}, numTriangles : { get : function () { return this.get_numTriangles (); }}});
// Statics
Polygon.createEllipse = function(x,y,radiusX,radiusY,numSides) {
if(numSides == null) {
numSides = -1;
}
return new (starling_geom_Ellipse().default)(x,y,radiusX,radiusY,numSides);
}
Polygon.createCircle = function(x,y,radius,numSides) {
if(numSides == null) {
numSides = -1;
}
return new (starling_geom_Ellipse().default)(x,y,radius,radius,numSides);
}
Polygon.createRectangle = function(x,y,width,height) {
return new (starling_geom_Rectangle().default)(x,y,width,height);
}
Polygon.isConvexTriangle = function(ax,ay,bx,by,cx,cy) {
return (ay - by) * (cx - bx) + (bx - ax) * (cy - by) >= 0;
}
Polygon.areVectorsIntersecting = function(ax,ay,bx,by,cx,cy,dx,dy) {
if(ax == bx && ay == by || cx == dx && cy == dy) {
return false;
}
var abx = bx - ax;
var aby = by - ay;
var cdx = dx - cx;
var cdy = dy - cy;
var tDen = cdy * abx - cdx * aby;
if(tDen == 0.0) {
return false;
}
var t = (aby * (cx - ax) - abx * (cy - ay)) / tDen;
if(t < 0 || t > 1) {
return false;
}
var s = aby != 0.0 ? (cy - ay + t * cdy) / aby : (cx - ax + t * cdx) / abx;
if(s >= 0.0) {
return s <= 1.0;
} else {
return false;
}
}
Polygon.sRestIndices = (openfl__$Vector_Vector_$Impl_$().default)._new()
// Export
exports.default = Polygon;