public Point3d at3DHeight( double h3 ) { double h = to2d (new Point3d(0,h3,0) ).y; int i = 0; while (get(i).y <= h && i < size() - 1) i++; if (i == 0) return null; else if (get(i).y <= h) return null; else return to3d( new Point2d( new Line(get(i-1), get(i)).xAtY( h ), h ) ); }
public static Point2d project(Line l, Point2d pt) { Vector2d v1 = new Vector2d(l.end); v1.sub(l.start); Vector2d v2 = new Vector2d(pt); v2.sub(l.start); double param = v2.dot(v1) / v1.length(); if (param < 0 || param > v1.length()) return null; v1.normalize(); v1.scale(param); v1.add(l.start); return new Point2d(v1); }
private static double[] findRange(SuperEdge se, Point2d s, Point2d e, Line backup ) { Line mf; if ( se.mini.isEmpty() || se.mini.get( 0 ).imageFeatures == null ) { if ( backup == null ) return null; else mf = backup; } else mf = se.mini.get(0).imageFeatures.mega.megafacade; // todo: bad place for this method. double mfL = mf.length(); return new double[] { mf.findPPram( s ) * mfL, mf.findPPram( e ) * mfL }; }
private boolean inBounds( Matrix4d mini, List<double[]> bounds ) { // mini matrix is in mini-mesh format: a translation from a 255^3 cube in the first quadrant // trans.offset is a transform from that space, into jme rendered space (cartesian in meters, around the origin) Matrix4d m = new Matrix4d(); m.mul( Jme3z.fromMatrix ( trans.offset ), mini ); for (Point2d p : Arrays.stream( cubeCorners ).map( c -> { Point3d tmp = new Point3d(); m.transform( c, tmp ); return new Point2d(tmp.x, tmp.z); }).collect( Collectors.toList() ) ) { for (double[] bound : bounds) { if ( bound[0] < p.x && bound[1] > p.x && bound[2] < p.y && bound[3] > p.y ) return true; } } return false; }
@Override public void blockSelected( LoopL<Point3d> polies, BlockGen blockGen ) { Point2d cen = Loopz.average( Loopz.to2dLoop( polies, 1, null ) ); for (File f : new File (tweed.DATA+File.separator +"solutions").listFiles()) { try { Point2d fp = FeatureCache.fileToCenter( f.getName() ); if (fp.distanceSquared( cen ) < 1) { new Thread( () -> load( f, true ) ).start(); return; } } catch (Throwable th) { System.out.println( "unable to read solution "+f.getName() ); } } JOptionPane.showMessageDialog( tweed.frame(), "Can't find solution for center " + cen ); }
public boolean matches(Line f) { if ( lf.angle( new LinearForm(f) ) < 0.1 && lf.distance( f.start ) < 3 ) { for ( Point2d pt : f.points() ) { double p = lf.findPParam( pt ); min = Math.min( min, p ); max = Math.max( max, p ); } facades.add(f); length += f.length(); return true; } return false; }
public double adjacentDist(Line l, Point2d pt) { Vector2d v1 = new Vector2d(l.end); v1.sub(l.start); Vector2d v2 = new Vector2d(pt); v2.sub(l.start); double param = v2.dot(v1) / v1.length(); if ( param < 0 || param > v1.length() ) return Double.MAX_VALUE; v1.normalize(); v1.scale( param ); v1.add( l.start ); return new Point2d (v1).distance(pt); }
@Override public List<Point2d> gen(Vector2d left, Vector2d right) { Point2d overhang = new Point2d(right); overhang.scale(0.2); Line l = new Line(new Point2d(), new Point2d(left)); Point2d r = l.project(overhang, false); List<Point2d> out = new ArrayList<>(); out.add(new Point2d()); out.add(overhang); out.add(r); return out; }
private static PtInChain findValid( List<Point2d> chain, double startingX, boolean left ) { double bestArea = -Double.MAX_VALUE; PtInChain bestPt = new PtInChain ( chain.get(0), 0, 0 ); double bestX = chain.get(0).x; Point2d pt; for (int i = 0; i < chain.size(); i++) { pt = chain.get(i); bestX = left ? Math.max (pt.x, bestX) : Math.min (pt.x, bestX); double area = Math.abs(startingX-bestX) * pt.y; if (area > bestArea || area == 0 && bestArea == 0 && pt.y > bestPt.y) { bestPt = new PtInChain( new Point2d ( bestX, pt.y), i, 0); bestArea = area; } } return bestPt; }
public static Point2d worldToLLong( Tweed tweed, Point3d cen ) { Point3d out = new Point3d( cen ); TweedSettings.settings.fromOrigin.transform( out ); try { double[] latLong = new double[3]; toLatLong.transform( new double[] { out.x, out.y, out.z }, 0, latLong, 0, 1 ); return new Point2d( latLong[ 0 ], latLong[ 1 ] ); } catch ( TransformException e ) { e.printStackTrace(); } return null; }
@Override public double getDistance( Point2d pt ) { pt = flip (pt); if ( contains( pt ) ) return 0; double dist = Double.MAX_VALUE; for ( Bounds b : new Bounds[] { XMIN, YMIN, XMAX, YMAX } ) { Line l = getAsRect().getEdge( b ); dist = Math.min( dist, l.distance( pt ) ); } return dist; }
@Override public void mouseDown( MouseEvent e, PanMouseAdaptor ma ) { Point2d pt = flip ( ma.from( e ) ); double bestDist = ma.fromZoom( 10 ); for (FRect f: getRects()) { double dist = f.getDistance( pt ); if (dist < bestDist) { bestDist = dist; dragging = f; } } if (dragging != null) dragging.mouseDown( e, ma ); }
@Override public void mouseDown( MouseEvent e, PanMouseAdaptor ma ) { double best = ma.fromZoom( 10 ); dragging = null; Point2d pt = lastPoint = flip ( ma.from( e ) ); for (Bounds b : new Bounds[] {XMIN, YMIN, XMAX, YMAX}) { double dist = getEdge(b).distance(pt); if (dist < best) { best = dist; dragging = b; } } // dragging == null means move whole rect }
@Override public void mouseDragged( MouseEvent e, PanMouseAdaptor ma) { Point2d pt = flip ( ma.from( e ) ); Point2d delta = new Point2d (pt); delta.sub( lastPoint ); if ( dragging == null ) { Point2d n = new Point2d( get( Bounds.XCEN ) + delta.x, get( Bounds.YCEN ) + delta.y ); set( Bounds.XCEN, n.x ); set( Bounds.YCEN, n.y ); } else { double value = get( dragging ) + ( dragging.name().charAt( 0 ) == 'Y' ? delta.y : delta.x ); set( dragging, value, true ); } lastPoint = pt; }
private R project (Point2d pt) { double bestDist = Double.MAX_VALUE; R best = null; double perim = 0; for (int i = 0; i < hull.size(); i++ ) { Point2d proj = hull.get(i).project(pt, true); double dist = proj.distanceSquared(pt); if (dist < bestDist) { bestDist = dist; best = new R (i, proj, perim + hull.get(i).start.distance(proj)); } perim += hull.get(i).length(); } return best; }
private boolean subdivide(AABB b) { double w = aabb.width/2d; double h = aabb.height/2d; if (w<minWidth || h<minHeight) return false; AxisAlignedBoundingBox aabbNW = new AxisAlignedBoundingBox(aabb,w,h); northWest = new MxCifQuadNode<AABB>(aabbNW); Point2d xyNE = new Point2d(aabb.x+w,aabb.y); AxisAlignedBoundingBox aabbNE = new AxisAlignedBoundingBox(xyNE,w,h); northEast = new MxCifQuadNode<AABB>(aabbNE); Point2d xySW = new Point2d(aabb.x,aabb.y+h); AxisAlignedBoundingBox aabbSW = new AxisAlignedBoundingBox(xySW,w,h); southWest = new MxCifQuadNode<AABB>(aabbSW); Point2d xySE = new Point2d(aabb.x+w,aabb.y+h); AxisAlignedBoundingBox aabbSE = new AxisAlignedBoundingBox(xySE,w,h); southEast = new MxCifQuadNode<AABB>(aabbSE); return insertIntoChildren(b); }
public BlockFeatures( File blockDir, Map<Point2d, BlockFeatures> blockFeatures ) { this.blockDir = blockDir; String name = blockDir.getName(); try { pos = fileToCenter( name ); blockFeatures.put(pos, this); } catch ( Throwable th ) { th.printStackTrace(); } }
public BlockFeatures getBlock( Point2d center ) { Optional<Point2d> maybePt = blockFeatures.keySet().stream().min( (a,b ) -> Double.compare( a.distance(center), b.distance(center) ) ); if (maybePt.isPresent()) { if (center.distance( maybePt.get() ) < 1) return blockFeatures.get(maybePt.get()); else { JOptionPane.showMessageDialog( tweed.frame.frame, "block features not found "+ center.x+"_" + center.y ); } } return new BlockFeatures(); }
public MFPoint( Point2d pt, Set<ImageFeatures> covering, MegaFeatures mega, ImageFeatures image, MiniFacade left, MiniFacade right ) { super(pt); this.mega = mega; this.covering = covering; this.image = image; this.left = left; this.right = right; }
@Override public void paint( Object o, Graphics2D g, PanMouseAdaptor ma ) { Prof p = (Prof)o; for (Pair<Point2d, Point2d> line : new ConsecutivePairs<>( p, false )) { // g.setColor( Color.black ); g.drawLine(ma.toX(line.first().x), ma.toY(-line.first().y), ma.toX(line.second().x), ma.toY(-line.second().y)); PaintThing.setBounds( line.first() ); // g.setColor( Color.red ); for (Point2d s : new Point2d[] {line.first(), line.second()}) { g.fillOval(ma.toX(s.x) - 4, ma.toY(-s.y) - 4, 8, 8); } } }
public void set(Point2d upperLeft, double width, double height) { set(upperLeft.x, upperLeft.y); this.width = width; this.height = height; minX = upperLeft.x; minY = upperLeft.y; maxX = upperLeft.x+width; maxY = upperLeft.y+height; }
protected Double verticalLength( double tol ) { double length = 0; for (Pair<Point2d, Point2d> pts : new ConsecutiveItPairs<>( this )) { Line line = new Line (pts.first(), pts.second()); double angle = line.aTan2(); if (angle > Mathz.PI2 - tol && angle < Mathz.PI2 + tol) length += line.length(); } return length; }
/** * {@inheritDoc} */ @Override public int compare(Point2d o1, Point2d o2) { if (o1.x < o2.x) return -1; if (o1.x > o2.x) return 1; return 0; }
public static HalfMesh2 boundMesh( List<Line> footprint ) { double[] minMax = minMax( 10, footprint ); HalfMesh2.Builder builder = new HalfMesh2.Builder( SuperEdge.class, SuperFace.class ); builder.newPoint( new Point2d( minMax[ 0 ], minMax[ 3 ] ) ); builder.newPoint( new Point2d( minMax[ 1 ], minMax[ 3 ] ) ); builder.newPoint( new Point2d( minMax[ 1 ], minMax[ 2 ] ) ); builder.newPoint( new Point2d( minMax[ 0 ], minMax[ 2 ] ) ); builder.newFace (); HalfMesh2 mesh = builder.done(); return mesh; }
public boolean containsPoint(Point2d p) { if (p.x>=maxX) return false; if (p.x<minX) return false; if (p.y>=maxY) return false; if (p.y<minY) return false; return true; }
private static Prof defaultProf( Prof example ) { Prof vertical = example == null ? new Prof() : new Prof( example ); vertical.clear(); vertical.add( new Point2d() ); vertical.add( new Point2d( 0, 20 ) ); return vertical; }
private void notBoth( HalfEdge e1, HalfEdge e2, boolean isContraint, double badThingsAreBad ) throws GRBException { GRBLinExpr no = new GRBLinExpr(); no.addTerm( 1, edgeInfo.get( e1 ).isEdge ); no.addTerm( 1, edgeInfo.get( e2 ).isEdge ); if (isContraint) { model.addConstr( no, GRB.LESS_EQUAL, 1, "bad geom < 1" ); } else { GRBVar bothSelected = model.addVar( 0.0, 1.0, 0, GRB.BINARY, BAD_GEOM); no.addTerm( -2, bothSelected ); model.addConstr( no, GRB.LESS_EQUAL, 1, "bad geom <" ); model.addConstr( no, GRB.GREATER_EQUAL, -0.5, "bad geom >" ); target.addTerm( badThingsAreBad, bothSelected ); { Line l1 = e1.line(), l2 = e2.line(); l1.start = new Point2d(l1.start); l1.end = new Point2d(l1.end ); l2.start = new Point2d(l2.start); l2.end = new Point2d(l2.end ); l1.moveLeft( -0.1 ); l2.moveLeft( -0.1 ); PaintThing.debug( new Color (255,170,0), 2, l1 ); PaintThing.debug( new Color (170,0,255), 2, l2 ); edgeInfo.get( e1 ).debug = bothSelected; } } }
public ToProject( Point2d s, Point2d e, double minHeight, double maxHeight ) { this.s = s; this.e = e; this.maxHeight = maxHeight; this.minHeight = minHeight; }
private double guessHeight( List<Point3d> meshPoints, Line l ) { double height; height = 2; // Line shortL = new Line (l.fromFrac( 0.1 ), l.fromFrac(0.9)); for ( Point3d pt : meshPoints ) { if ( adjacentDist( l, new Point2d( pt.x, pt.z ) ) < 2 ) height = Math.max( height, pt.y ); } return height; }
public static double distanceSquared(Point2d a, Line l) { Point2d b = project (l, a); if (a == null || b == null) return -Double.MAX_VALUE; return a.distanceSquared(b); }
public Longer (Line l2, double expand) { double tol = l2.length() * expand; set (new Point2d ( Math.min (l2.start.x, l2.end.x) - tol, Math.min (l2.start.y, l2.end.y) - tol), Math.abs( l2.end.x - l2.start.x ) + 2 * tol, Math.abs( l2.end.y - l2.start.y ) + 2 * tol ); this.line = l2; }
private static int compare (Point2d a, Point2d b) { int xComp = X_COMPARATOR.compare(a, b); if (xComp != 0) return xComp; return Y_COMPARATOR.compare(a, b); }
private static double[] findSE( MiniFacade mf, Line l, List<Face> chain ) { double mlen = l.length(); double lowest = Double.MAX_VALUE; Face bestFace = null; for (Face f : chain) { double[] bounds = Loopz.minMax( f.getLoopL() ); if (bounds[5] - bounds[4] > 1 && bounds[4] < lowest) { bestFace = f; lowest = bounds[4]; } } if (bestFace == null) return new double[] {mf.left, mf.left+ mf.width}; //! List<Double> params = bestFace.getLoopL().streamE().map( p3 -> l.findPPram( new Point2d ( p3.x, p3.y ) ) ).collect( Collectors.toList() ); double[] out = new double[] { params.stream().mapToDouble( x->x ).min().getAsDouble() * mlen, params.stream().mapToDouble( x->x ).max().getAsDouble() * mlen }; // if good, stretch whole minifacade to mesh if ( Mathz.inRange( ( out[1] - out[0]) / (mf.width), 0.66, 1.4 ) ) return out; // else snap to the closest of start/end if ( l.fromPPram( out[0] / mlen ).distance( l.fromPPram( mf.left / mlen ) ) > l.fromPPram( out[1] / mlen ).distance( l.fromPPram( (mf.left + mf.width ) / mlen ) ) ) return new double[] {out[1] - mf.width, out[1]}; else return new double[] {out[0], out[0] + mf.width }; }
public QuadF( FRect rect, Line megafacade ) { this.original = rect; double mLen = megafacade .length(); Point2d l = megafacade.fromPPram( rect.x / mLen ), r = megafacade.fromPPram( ( rect.x + rect.width ) / mLen ); corners[0] = Pointz.to3( l, rect.y ); corners[1] = Pointz.to3( l, rect.y + rect.height ); corners[2] = Pointz.to3( r, rect.y + rect.height ); corners[3] = Pointz.to3( r, rect.y ); }
public void setBounds( Matrix4d to2d, FRect bounds ) { List<Point2d> envelop = new ArrayList<>(); for (int i = 0; i < 4; i++) { Point3d tmp = new Point3d(corners[i]); to2d.transform( tmp ); envelop.add( Pointz.to2( tmp ) ); } bounds.setFrom( new DRectangle( envelop ) ); }
protected DRectangle findRect( Loop<Point2d> rect ) { double[] bounds = Loopz.minMax2d( rect ); DRectangle all = new DRectangle( bounds[0], bounds[2], bounds[1] - bounds[0], bounds[3] - bounds[2] ); return all; }
protected boolean visible( DRectangle dRectangle, List<DRectangle> occlusions ) { for (Point2d p : dRectangle.points()) for (DRectangle d : occlusions) if (d.contains( p )) return false; return true; }
private static Loop<Point2d> toPoly( List<Point2d> left, PtInChain xyL ) { Loop<Point2d> lef = new Loop<>(); for (int i = 0; i <= xyL.prevPt; i++) lef.append (left.get(i)); if (xyL.frac > 0 && xyL.prevPt < left.size()-1) lef.append (new Line ( left.get ( xyL.prevPt ), left.get(xyL.prevPt + 1)).fromPPram( xyL.frac ) ); lef.append( new Point2d(xyL.x, xyL.y) ); lef.append( new Point2d(xyL.x, 0) ); return lef; }
private static PtInChain setToHeight( List<Point2d> chain, boolean left, double x2, double y2 ) { double bestX = chain.get(0).x; for (int i = 1; i < chain.size(); i++) { Point2d p = chain.get(i-1), n = chain.get(i); bestX = left ? Math.max (p.x, bestX) : Math.min (p.x, bestX); PtInChain first = new PtInChain( new Point2d ( n ), i, 0 ); first.x = bestX; if (Math.abs(n.y-y2) < 0.001) { first.x = left ? Math.max (n.x, first.x) : Math.min (n.x, first.x); return first; } Line pn = new Line(p, n); if (n.y > y2) { Point2d sec = new LinearForm(pn).intersect( new LinearForm( 0, 1, y2 ) ); if (sec == null) return first; sec.x = left ? Math.max (bestX, sec.x) : Math.min (bestX, sec.x); return new PtInChain( sec, i-1, pn.findPPram( sec ) ); } } return null; }
private Point2d getRectPoint( FRect w, Dir dir ) { switch (dir) { case D: return new Point2d(w.x + w.width/2, w.y ); case U: return new Point2d(w.x + w.width/2, w.y + w.height); case L: return new Point2d(w.x , w.y + w.height/2); case R: default: return new Point2d(w.x + w.width , w.y + w.height/2); } }