Skip to content

Commit

Permalink
prune cells more aggressively for better memory footprint, close #82
Browse files Browse the repository at this point in the history
  • Loading branch information
mourner committed Jun 26, 2024
1 parent 3e2a83e commit d3357ec
Showing 1 changed file with 24 additions and 18 deletions.
42 changes: 24 additions & 18 deletions polylabel.js
Original file line number Diff line number Diff line change
Expand Up @@ -29,42 +29,48 @@ export default function polylabel(polygon, precision = 1.0, debug = false) {
// a priority queue of cells in order of their "potential" (max distance to polygon)
const cellQueue = new Queue(undefined, compareMax);

// cover polygon with initial cells
for (let x = minX; x < maxX; x += cellSize) {
for (let y = minY; y < maxY; y += cellSize) {
cellQueue.push(new Cell(x + h, y + h, h, polygon));
}
}

// take centroid as the first best guess
let bestCell = getCentroidCell(polygon);

// second guess: bounding box centroid
const bboxCell = new Cell(minX + width / 2, minY + height / 2, 0, polygon);
if (bboxCell.d > bestCell.d) bestCell = bboxCell;

let numProbes = cellQueue.length;
let numProbes = 2;

while (cellQueue.length) {
// pick the most promising cell from the queue
const cell = cellQueue.pop();
function potentiallyQueue(x, y, h) {
const cell = new Cell(x, y, h, polygon);
numProbes++;
if (cell.max > bestCell.d + precision) cellQueue.push(cell);

// update the best cell if we found a better one
if (cell.d > bestCell.d) {
bestCell = cell;
if (debug) console.log('found best %f after %d probes', Math.round(1e4 * cell.d) / 1e4, numProbes);
if (debug) console.log(`found best ${Math.round(1e4 * cell.d) / 1e4} after ${numProbes} probes`);
}
}

// cover polygon with initial cells
let h = cellSize / 2;
for (let x = minX; x < maxX; x += cellSize) {
for (let y = minY; y < maxY; y += cellSize) {
potentiallyQueue(x + h, y + h, h);
}
}

while (cellQueue.length) {
// pick the most promising cell from the queue
const cell = cellQueue.pop();

// do not drill down further if there's no chance of a better solution
if (cell.max - bestCell.d <= precision) continue;
if (cell.max - bestCell.d <= precision) break;

// split the cell into four cells
h = cell.h / 2;
cellQueue.push(new Cell(cell.x - h, cell.y - h, h, polygon));
cellQueue.push(new Cell(cell.x + h, cell.y - h, h, polygon));
cellQueue.push(new Cell(cell.x - h, cell.y + h, h, polygon));
cellQueue.push(new Cell(cell.x + h, cell.y + h, h, polygon));
numProbes += 4;
potentiallyQueue(cell.x - h, cell.y - h, h);
potentiallyQueue(cell.x + h, cell.y - h, h);
potentiallyQueue(cell.x - h, cell.y + h, h);
potentiallyQueue(cell.x + h, cell.y + h, h);
}

if (debug) {
Expand Down

0 comments on commit d3357ec

Please sign in to comment.