concurrent refactor. added clipping. all toggled with experimental

This commit is contained in:
Stewart Allen 2021-06-20 18:10:19 -04:00
commit 881992b52e
3 changed files with 88 additions and 28 deletions

View file

@ -6,7 +6,11 @@ let BASE = self.base,
KIRI = self.kiri,
UTIL = BASE.util,
POLY = BASE.polygons,
CODEC = KIRI.codec;
CODEC = KIRI.codec,
clib = self.ClipperLib,
ctyp = clib.ClipType,
ptyp = clib.PolyType,
cfil = clib.PolyFillType;
// catch clipper alerts and convert to console messages
self.alert = function(o) {
@ -56,6 +60,23 @@ const funcs = {
reply({ fill: arr }, [ arr.buffer ]);
},
clip: data => {
let clip = new clib.Clipper();
let ctre = new clib.PolyTree();
let clips = [];
clip.AddPaths(data.lines, ptyp.ptSubject, false);
clip.AddPaths(data.polys, ptyp.ptClip, true);
if (clip.Execute(ctyp.ctIntersection, ctre, cfil.pftNonZero, cfil.pftEvenOdd)) {
for (let node of ctre.m_AllPolys) {
clips.push(CODEC.encode(POLY.fromClipperNode(node, data.z)));
}
}
reply({ clips });
},
bad: data => {
reply({error: "invalid command"});
}

View file

@ -34,10 +34,13 @@ if (concurrent) {
// for concurrent operations
const minwork =
KIRI.minions = {
concurrent,
union: function(polys, minarea) {
return new Promise((resolve, reject) => {
if (concurrent === 0 || polys.length * 2 < concurrent) {
resolve(POLY.union(polys, 0, true));
return;
}
let polyper = Math.ceil(polys.length / concurrent);
let running = 0;
@ -64,6 +67,7 @@ KIRI.minions = {
return new Promise((resolve, reject) => {
if (concurrent === 0) {
resolve(POLY.fillArea(polys, angle, spacing, [], minLen, maxLen));
return;
}
minwork.queue({
cmd: "fill",
@ -83,6 +87,30 @@ KIRI.minions = {
});
},
clip: function(slice, polys, lines) {
return new Promise((resolve, reject) => {
if (concurrent === 0) {
reject("concurrent clip unavaiable");
}
minwork.queue({
cmd: "clip",
polys: POLY.toClipper(polys),
lines: lines.map(a => a.map(p => p.toClipper())),
z: slice.z
}, data => {
let polys = KIRI.codec.decode(data.clips);
for (let top of slice.tops) {
for (let poly of polys) {
if (poly.isInside(top.poly)) {
top.fill_sparse.push(poly);
}
}
}
resolve(polys);
});
});
},
queue: function(work, ondone) {
minionq.push({work, ondone});
minwork.kick();