RandomConvexPolygons = (function() {
const __getRandomInRange = function(min,max) {
return Math.random() * (max - min) + min;
}
const __getIntRandomInRange = function(min,max) {
return Math.floor(__getRandomInRange(min,max));
}
const __randomPolygon = function(minangles,maxangles) {
const n = __getIntRandomInRange(minangles,maxangles);
let angles = Array(n).fill().map(() => __getRandomInRange(0,2*Math.PI));
angles.sort((a,b) => a-b);
const poly = angles.map((angle) => [Math.cos(angle),Math.sin(angle)]);
poly.push(poly[0]);
return poly;
}
const __randomScale = function(poly,minscale,maxscale) {
const sx = __getRandomInRange(minscale,maxscale);
const sy = __getRandomInRange(minscale,maxscale);
return poly.map((vtx) => [vtx[0]*sx,vtx[1]*sy]);
}
const __randomTranslate = function(poly,bbox,trunctoint) {
let polyinbbox = false;
let transpoly;
while (!polyinbbox) {
const xcenter = __getRandomInRange(bbox[0],bbox[2]);
const ycenter = __getRandomInRange(bbox[1],bbox[3]);
transpoly = poly.map((vtx) => [vtx[0]+xcenter,vtx[1]+ycenter]);
if (trunctoint) {
transpoly = transpoly.map((vtx) => [Math.floor(vtx[0]),Math.floor(vtx[1])]);
}
polyinbbox = transpoly.reduce((prev,curr) => (prev && curr[0] >= bbox[0] && curr[1] >= bbox[1] && curr[0] <= bbox[2] && curr[1] <= bbox[3]));
}
return transpoly;
}
class RCP {
constructor(bbox,numpolys,minangles,maxangles,maxscale) {
this.bbox = bbox;
this.numpolys = numpolys;
this.minangles = minangles;
this.maxangles = maxangles;
this.maxscale = maxscale;
}
generate() {
const mindimension = Math.min(this.bbox[2]-this.bbox[0],this.bbox[3]-this.bbox[1]);
let polygons = [];
while (polygons.length < this.numpolys) {
let newpolygon = __randomPolygon(this.minangles,this.maxangles);
newpolygon = __randomScale(newpolygon,this.maxscale/2,this.maxscale);
newpolygon = __randomTranslate(newpolygon,this.bbox,true);
polygons.push(newpolygon);
}
return polygons;
}
}
return RCP;
})();