use of com.badlogic.gdx.utils.LongMap in project gaiasky by langurmonkey.
the class OctreeGeneratorMag method generateOctree.
@Override
public OctreeNode generateOctree(List<IParticleRecord> catalog) {
root = IOctreeGenerator.startGeneration(catalog, params);
// Holds all octree nodes indexed by id
LongMap<OctreeNode> idMap = new LongMap<>();
idMap.put(root.pageId, root);
// Contains the list of objects for each node
Map<OctreeNode, List<IParticleRecord>> objMap = new HashMap<>();
int catalogSize = catalog.size();
int catalogIndex = 0;
for (int level = 0; level <= 19; level++) {
logger.info("Generating level " + level + " (" + (catalog.size() - catalogIndex) + " stars left)");
while (catalogIndex < catalogSize) {
// Add stars to nodes until we reach max part
IParticleRecord sb = catalog.get(catalogIndex++);
double x = sb.x();
double y = sb.y();
double z = sb.z();
Long nodeId = getPositionOctantId(x, y, z, level);
if (!idMap.containsKey(nodeId)) {
// Create octant and parents if necessary
OctreeNode octant = createOctant(nodeId, x, y, z, level);
// Add to idMap
idMap.put(octant.pageId, octant);
}
// Add star to node
OctreeNode octant = idMap.get(nodeId);
int addedNum = addStarToNode(sb, octant, objMap);
if (addedNum >= params.maxPart) {
// On to next level!
break;
}
}
if (catalogIndex >= catalog.size()) {
// All stars added -> FINISHED
break;
}
}
if (params.postprocess) {
logger.info("Post-processing octree: childcount=" + params.childCount + ", parentcount=" + params.parentCount);
long mergedNodes = 0;
long mergedObjects = 0;
// We merge low-count nodes (<= childcount) with parents, if parents' count is <= parentcount
Object[] nodes = objMap.keySet().toArray();
// Sort by descending depth
Arrays.sort(nodes, (node1, node2) -> {
OctreeNode n1 = (OctreeNode) node1;
OctreeNode n2 = (OctreeNode) node2;
return Integer.compare(n2.depth, n1.depth);
});
int n = objMap.size();
for (int i = n - 1; i >= 0; i--) {
OctreeNode current = (OctreeNode) nodes[i];
if (current.numChildren() == 0 && current.parent != null && objMap.containsKey(current) && objMap.containsKey(current.parent)) {
List<IParticleRecord> childArr = objMap.get(current);
List<IParticleRecord> parentArr = objMap.get(current.parent);
if (childArr.size() <= params.childCount && parentArr.size() <= params.parentCount) {
// Merge children nodes with parent nodes, remove children
parentArr.addAll(childArr);
objMap.remove(current);
current.remove();
mergedNodes++;
mergedObjects += childArr.size();
}
}
}
logger.info("POSTPROCESS STATS:");
logger.info(" Merged nodes: " + mergedNodes);
logger.info(" Merged objects: " + mergedObjects);
}
// Tree is ready, create star groups
Set<OctreeNode> nodes = objMap.keySet();
for (OctreeNode node : nodes) {
List<IParticleRecord> list = objMap.get(node);
StarGroup sg = new StarGroup();
sg.setData(list, false);
node.add(sg);
sg.octant = node;
sg.octantId = node.pageId;
}
root.updateCounts();
return root;
}
Aggregations