Initial commit for historical purposes

This commit is contained in:
2025-05-02 00:29:08 -04:00
commit a1899a52b7
64 changed files with 7754 additions and 0 deletions

View File

@@ -0,0 +1,194 @@
package com.aaaaahhhhhhh.bananapuncher714.tess4j;
import java.lang.reflect.Field;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Iterator;
import java.util.List;
import java.util.Optional;
import org.joml.Math;
public class Util {
protected static String toString( Object obj ) {
StringBuilder builder = new StringBuilder();
builder.append( obj.getClass().getSimpleName() );
builder.append( '{' );
List< Field > fields = new ArrayList< Field >();
fields.addAll( Arrays.asList( obj.getClass().getDeclaredFields() ) );
fields.addAll( Arrays.asList( obj.getClass().getFields() ) );
for ( Iterator< Field > it = fields.iterator(); it.hasNext(); builder.append( "," ) ) {
Field field = it.next();
builder.append( field.getName() );
builder.append( '=' );
try {
builder.append( field.get( obj ) );
} catch ( IllegalArgumentException | IllegalAccessException e ) {
builder.append( "?" );
}
}
builder.append( '}' );
return builder.toString();
}
public static Optional< Point > intersection( final VertexOld x1, final VertexOld x2, final VertexOld x3, final VertexOld x4 ) {
Point point = null;
final Vector2dOld p = x1.toVector();
final Vector2dOld r = x2.subtract( x1 );
final Vector2dOld q = x3.toVector();
final Vector2dOld s = x4.subtract( x3 );
final Vector2dOld qp = q.subtract( p );
final double qpr = qp.cross( r );
final double rs = r.cross( s );
// Are the two lines parallel
if ( rs == 0 ) {
final Vector2dOld u = x2.toVector();
final Vector2dOld v = x4.toVector();
// For normalizing against pr
final double rr = r.dot( r );
// t0 and t1 represent the distance of the second edge endpoints relative to the first edge normalized by r
// t0 = ( ( q - p ) . r ) / rr;
double t0 = qp.dot( r ) / rr;
// t1 = ( ( q + s - p ) . r ) / rr
double t1 = v.subtract( p ).dot( r ) / rr;
// If the vectors are pointing in the opposite directions, then swap t0 and t1
final boolean inverted = s.dot( r ) < 0;
if ( inverted ) {
double temp = t0;
t0 = t1;
t1 = temp;
}
if ( qpr == 0 ) {
if ( t0 < 1 & t1 > 0 ) {
final double midt = Math.max( t0, 0 ) + Math.min( t1, 1 ) / 2.0;
final Vector2dOld midpoint = r.multiply( midt ).add( p );
point = midpoint.toPoint();
} else {
final Vector2dOld pu = t0 > 1 ? u : p;
// Same as the first edge but the second edge may be inverted
final Vector2dOld qv = ( inverted ^ t0 > 1 ) ? q : v;
final Vector2dOld midpoint = pu.add( qv ).divide( 2.0 );
point = midpoint.toPoint();
}
}
} else {
// Calculate t and u
final double t = qp.cross( s ) / rs;
final double u = qpr / rs;
// Do the line segments intersect
if ( t >= 0 && t <= 1 && u >= 0 && u <= 1 ) {
// Calculate the point of intersection
final Vector2dOld intersection = r.multiply( t ).add( p );
point = intersection.toPoint();
}
}
return Optional.ofNullable( point );
}
// https://stackoverflow.com/questions/563198/how-do-you-detect-where-two-line-segments-intersect
// Vector based closest intersection method
public static Point closestPoint( final VertexOld x1, final VertexOld x2, final VertexOld x3, final VertexOld x4 ) {
Point point = new Point( 0, 0 );
final Vector2dOld p = x1.toVector();
final Vector2dOld r = x2.subtract( x1 );
final Vector2dOld q = x3.toVector();
final Vector2dOld s = x4.subtract( x3 );
final Vector2dOld qp = q.subtract( p );
final double qpr = qp.cross( r );
final double rs = r.cross( s );
// Are the two lines parallel
if ( rs == 0 ) {
final Vector2dOld u = x2.toVector();
final Vector2dOld v = x4.toVector();
// For normalizing against pr
final double rr = r.dot( r );
// t0 and t1 represent the distance of the second edge endpoints relative to the first edge normalized by r
// t0 = ( ( q - p ) . r ) / rr;
double t0 = qp.dot( r ) / rr;
// t1 = ( ( q + s - p ) . r ) / rr
double t1 = v.subtract( p ).dot( r ) / rr;
// If the vectors are pointing in the opposite directions, then swap t0 and t1
final boolean inverted = s.dot( r ) < 0;
if ( inverted ) {
double temp = t0;
t0 = t1;
t1 = temp;
}
// Do the lines overlap
if ( t0 < 1 && t1 > 0 ) {
// The midpoint is an arbitrary point that just happens to look good as an intersection
// Find the midpoint between the overlapping region
final double midt = Math.max( t0, 0 ) + Math.min( t1, 1 ) / 2.0;
// If colinear
if ( qpr == 0 ) {
// Do not need to calculate the distance between the two parallel lines since it is 0
final Vector2dOld midpoint = r.multiply( midt ).add( p );
point.x = midpoint.x;
point.y = midpoint.y;
} else {
// Calculate the midpoint along pr
final Vector2dOld midp = r.multiply( midt ).add( p );
// Calculate the perpendicular distance between both lines
final Vector2dOld perp = r.perpendicular();
final Vector2dOld z = perp.multiply( qp.dot( perp ) / rr );
// Sum the components
final Vector2dOld midpoint = midp.add( z.divide( 2.0 ) );
point.x = midpoint.x;
point.y = midpoint.y;
}
} else {
// The lines aren't really anywhere close to each other, so just find the midpoint between the 2 closest points
// If t0 > 1, then the second edge must lie to the right of the first edge
final Vector2dOld pu = t0 > 1 ? u : p;
// Same as the first edge but the second edge may be inverted
final Vector2dOld qv = ( inverted ^ t0 > 1 ) ? q : v;
final Vector2dOld midpoint = pu.add( qv ).divide( 2.0 );
point.x = midpoint.x;
point.y = midpoint.y;
}
} else {
// Calculate t and u
final double t = qp.cross( s ) / rs;
final double u = qpr / rs;
// Do the line segments intersect
if ( t >= 0 && t <= 1 && u >= 0 && u <= 1 ) {
// Calculate the point of intersection
final Vector2dOld intersection = r.multiply( t ).add( p );
point.x = intersection.x;
point.y = intersection.y;
} else {
// No intersection, so calculate the closest point between the two segments
// We have t and u, which we can use to find the closest endpoints
final double nearT = Math.max( Math.min( t, 1 ), 0 );
final double nearU = Math.max( Math.min( u, 1 ), 0 );
final Vector2dOld nearP = r.multiply( nearT ).add( p );
final Vector2dOld nearQ = s.multiply( nearU ).add( q );
point.x = ( nearP.x + nearQ.x ) / 2.0;
point.y = ( nearP.y + nearQ.y ) / 2.0;
}
}
return point;
}
}