use of org.twak.utils.collections.Loop in project chordatlas by twak.
the class GISGen method initGML.
public void initGML() {
Closer<Point3d> closer = new Closer<>();
LoopL<Point3d> polies = null;
try {
polies = GMLReader.readGML3d(Tweed.toWorkspace(new File(gmlFile)), DefaultGeocentricCRS.CARTESIAN, CRS.decode(crs));
} catch (NoSuchAuthorityCodeException e) {
e.printStackTrace();
return;
} catch (FactoryException e) {
e.printStackTrace();
return;
}
Optional<Gen> hg = tweed.frame.gens(HeightGen.class).stream().findAny();
if (hg.isPresent())
for (Loop<Point3d> poly : polies) {
if (poly instanceof SuperLoop) {
SuperLoop sl = ((SuperLoop) poly);
sl.properties.putAll(((HeightGen) hg.get()).getProperties((String) sl.properties.get("name")));
}
}
for (Loop<Point3d> poly : polies) {
List<Point3d> points = new ArrayList();
for (Pair<Point3d, Point3d> pair : poly.pairs()) {
TweedSettings.settings.toOrigin.transform(pair.first());
pair.first().y = 0;
points.add(pair.first());
lines.add(new Line3d(pair.first(), pair.second()));
}
if (TweedSettings.settings.flipFootprints)
poly.reverse();
closer.add(points.toArray(new Point3d[points.size()]));
}
createBlocks(closer, polies);
}
use of org.twak.utils.collections.Loop in project chordatlas by twak.
the class SkelGen method buildCamp.
private static PlanSkeleton buildCamp(SuperFace sf, Double cap) {
Plan plan = new Plan();
LoopL<Bar> loopl = new LoopL();
Loop<Bar> loop = new Loop();
loopl.add(loop);
Cache<Point2d, Point2d> cache = new Cache<Point2d, Point2d>() {
@Override
public Point2d create(Point2d i) {
return new Point2d(i.x, i.y);
}
};
LoopL<HalfEdge> edges = sf.findHoles();
LoopL<Point2d> lpd = new LoopL();
for (Loop<HalfEdge> loopHE : edges) {
Map<Point2d, SuperEdge> ses = new HashMap();
Loop<Point2d> lp = new Loop();
lpd.add(lp);
for (HalfEdge he : loopHE) {
SuperEdge se = (SuperEdge) he;
lp.append(se.start);
ses.put(se.start, se);
}
lp = Loopz.mergeAdjacentEdges2(lp, 0.001);
for (Loopable<Point2d> lpb : lp.loopableIterator()) {
Bar b = new Bar(cache.get(lpb.getNext().get()), cache.get(lpb.get()));
SuperEdge se = ses.get(lpb.get());
Profile profile = null;
if (se.prof == null || se.prof.size() < 2) {
List<Point2d> defpts = new ArrayList<>();
defpts.add(new Point2d(0, 0));
defpts.add(new Point2d(0, -sf.height * 1.2));
profile = new Profile(defpts);
} else {
profile = toProfile(se.prof);
}
tagWalls(profile, ((SuperFace) se.face).roofColor, se, lpb.get(), lpb.getNext().get());
plan.addLoop(profile.points.get(0), plan.root, profile);
b.tags.add(new SETag(se));
loop.prepend(b);
plan.profiles.put(b, profile);
}
}
plan.points = loopl;
if (cap != null) {
// skel.capAt( cap, a -> skel.capArea = a ); simple...but doesn't show in the siteplan ui
Ship s = new FlatRoofShip(cap, plan);
for (Profile prof : plan.profiles.values()) {
for (Loop<Bar> lb : prof.points) {
boolean addedMarker = false;
for (Bar b : lb) {
if (-b.start.y < cap && -b.end.y > cap || (!addedMarker && b == lb.start.getPrev().get())) {
Marker m = new Marker();
m.set(b.toLine().xAtY(-cap), -cap);
m.bar = b;
m.bar.mould.create(m, null);
Instance i = s.newInstance();
i.anchors[0].setProfileGen(m.generator);
addedMarker = true;
}
}
}
}
plan.ships.add(s);
}
PlanSkeleton skel = new PlanSkeleton(plan);
skel.skeleton();
return skel;
}
use of org.twak.utils.collections.Loop in project chordatlas by twak.
the class Concarnie method tidy.
private void tidy(Graph2D graph) {
UnionWalker uw = new UnionWalker();
for (Point2d a : graph.map.keySet()) {
for (Line l : graph.get(a)) {
uw.addEdge(l.start, l.end);
// PaintThing.debug.put("flibble", l);
}
}
out = uw.findAll();
// if (false)
for (Loop<Point2d> loop : out) {
for (Loopable<Point2d> pt : loop.loopableIterator()) {
Line prev = findSupporting(pt, 1), next = findSupporting(pt, -1);
if (prev != null && next != null) {
Point2d bestFit = prev.intersects(next, false);
if (bestFit != null && pt.get().distance(bestFit) < P.CON_TOL && // if nearer other ends of lines, don't use
bestFit.distanceSquared(prev.start) < bestFit.distanceSquared(prev.end) && bestFit.distanceSquared(next.end) < bestFit.distanceSquared(next.start)) {
pt.get().set(bestFit);
}
}
}
}
Iterator<Loop<Point2d>> lit = out.iterator();
// if (false)
while (lit.hasNext()) {
Loop<Point2d> loop = lit.next();
Loopable<Point2d> start = loop.start, current = start;
int size = loop.count();
boolean again;
do {
again = false;
Point2d a = current.getPrev().get(), b = current.get(), c = current.getNext().get();
Line ab = new Line(a, b), bc = new Line(b, c);
double angle = Anglez.dist(ab.aTan2(), bc.aTan2());
if (// corner filter moves corners to same point!
a.distanceSquared(b) < 0.0001 || b.distanceSquared(c) < 0.0001 || // nearly parallel, but small area removed
angle < 0.2 && Math.abs(Mathz.area(a, b, c)) < 50 * P.CON_TOL * P.CON_TOL) // ab.length() + bc.length() > TOL/2 &&
// angle > Math.PI - 0.1 ) // pointy corner
// a.distanceSquared(c) < 0.0001 )
{
current.getPrev().setNext(current.getNext());
current.getNext().setPrev(current.getPrev());
size--;
if (start == current)
loop.start = start = current.getPrev();
again = true;
current = current.getPrev();
} else
current = current.getNext();
} while ((again || current != start) && size > 2);
if (size <= 2)
lit.remove();
}
}
use of org.twak.utils.collections.Loop in project chordatlas by twak.
the class SkelFootprint method dbgShowProfiles.
private void dbgShowProfiles(HalfMesh2 mesh, List<Prof> globalProfs, Map<SuperEdge, double[]> profFit, String name) {
Node n = new Node();
Jme3z.removeAllChildren(n);
int colI = 0;
for (HalfFace f : mesh) {
ColorRGBA col = Jme3z.toJme(Rainbow.getColour(colI++));
colI = colI % 6;
Material mat = new Material(tweed.getAssetManager(), "Common/MatDefs/Light/Lighting.j3md");
mat.setColor("Diffuse", col);
mat.setColor("Ambient", col);
mat.setBoolean("UseMaterialColors", true);
if (true) {
Loop<Point3d> loop = new Loop<>();
for (HalfEdge e : f) loop.append(new Point3d(e.start.x, 0, e.start.y));
MeshBuilder mb = new MeshBuilder();
mb.add(loop.singleton(), null, false);
Geometry g = new Geometry("floorplan", mb.getMesh());
g.setMaterial(mat);
n.attachChild(g);
}
for (HalfEdge e : f) {
SuperEdge se = (SuperEdge) e;
Prof bestProf = null;
if (globalProfs == null)
bestProf = se.prof;
else {
// if (se.profLine != null) {
//
// SuperLine sl = ((SuperLine)se.profLine);
// MegaFacade mf = (MegaFacade) sl.properties.get( MegaFacade.class.getName() );
//
// List<Prof> pfs = mf.getTween( se.start, se.end, 0.3 );
//
// if (!pfs.isEmpty())
// bestProf = Prof.parameterize( sl, pfs );
// else {
// bestProf = clean.get( 0 );
// double bestScore = Double.MAX_VALUE;
//
// for ( Prof c : clean ) {
//
// double score = 0;
// boolean good = false;
// for ( Prof r : mf.getTween( se.start, se.end, 0.3 ) ) {
// score += c.distance( r, true, false, true );
// good = true;
// }
// if ( good && score < bestScore ) {
// bestScore = score;
// bestProf = c;
// }
//
// }
// }
//
//
// }
// if (bestProf)
// ((SuperLine))
//
double[] fitV = profFit.get(se);
if (fitV == null)
continue;
double bestScore = Double.MAX_VALUE;
for (int ii = 0; ii < fitV.length; ii++) {
double d = fitV[ii];
if (d < bestScore) {
bestScore = d;
bestProf = globalProfs.get(ii);
}
}
//
// double bestScore = Double.MAX_VALUE;
//
// for ( int ii = 0; ii < fitV.length; ii++ ) {
// double d = fitV[ ii ];
// if ( d < bestScore ) {
// bestScore = d;
// bestProf = globalProfs.get( ii );
// }
// }
// if (false)
// se.prof = bestProf;
}
if (bestProf != null) {
Geometry g = new Geometry();
Point3d cen = Pointz.to3(se.line().fromPPram(0.5));
Prof goodOrientation = Prof.buildProfile(Pointz.to3(se.line()), cen);
for (Point2d p : bestProf) goodOrientation.add(p);
g.setMesh(goodOrientation.renderStrip(1.5, cen));
g.setMaterial(mat);
n.attachChild(g);
g.updateGeometricState();
g.updateModelBound();
}
}
}
skelGen.tweed.frame.addGen(new JmeGen(name, tweed, n), false);
}
use of org.twak.utils.collections.Loop in project chordatlas by twak.
the class VizSkelGen method calculate.
@Override
public void calculate() {
for (Spatial s : gNode.getChildren()) s.removeFromParent();
SuperFace sf;
if (mode == Mode.Extrude) {
sf = toHalf(Loopz.to3d(Loopz.removeInnerEdges(Loopz.toXZLoop(blockGen.polies)).get(0), 0, 1));
PlanSkeleton skel = calc(sf);
setSkel(skel, skel.output, sf);
} else
for (Loop<Point3d> loop : blockGen.polies) {
sf = toHalf(loop);
PlanSkeleton skel = calc(sf);
setSkel(skel, skel.output, sf);
}
gNode.updateModelBound();
gNode.updateGeometricState();
setVisible(visible);
}
Aggregations