I don't know Java, but I tried to understand your code.
I see, first of all, that you are applying Cartesian geometry with geographic coordinates. That is a known error for all non-terraplanist people.
But let's believe for a moment that the Earth is flat and that the geographic coordinates form a rectangular grid on a plane, in which you can add or subtract degrees and meters without noticing the difference.
You are getting the coordinates of a point far away from de middle point of a line, a distance of LENGTH * sqrt(2)
, in a North-East direction, and other point at the same distance in a South-West direction.
Then, you are getting the ellipsoidal distance from the end point of a line, to both coordinates pairs that you got before. And using a logic that the smaller distance will be to the point that you want.
But is the line SW - NE oriented? If the line is NW - SE oriented instead, you must have the same distance to both points (not really true in a non-terraplanist environment). If it is oriented S - N, the points are not on the line. Indeed, the points are not on the line except that the line is SW - NE oriented.
If the orientation of the line is fixed at what we say 45 degrees azimuth, then the only errors with your code is the distance to the points, and the addition and subtraction between angular and linear units. The second one can't be fixed.
I don't know geotools
neither. But I see that geographiclib
is implemented there to solve the Inverse problem of geodesy: knowing two points, get the geodesic line that unites them.
There is also a Direct problem of geodesy: knowing one point, the forward azimuth and a length over a geodesic line, get the second point.
So the logic that you need is: get the initial azimuth of the geodesic line that starts at the middle point and ends at the end point, solving the Inverse problem.
Then, get the point that you want solving the Direct problem, from the middle point, with the forward azimuth that you got before, and the given distance.
The code may look like:
GeodesicData inverse_solution = Geodesic.WGS84.Inverse(mid.y, mid.x, end.getY(), end.getX());
double forward_azimuth = inverse_solution.az1
GeodesicData direct_solution = Geodesic.WGS84.Direct(mid.y, mid.x, forward_azimuth, LENGTH);
double wanted_x = direct_solution.lon2;
double wanted_y = direct_solution.lat2;