mirror of
https://github.com/PhotonVision/photonvision
synced 2026-06-20 00:51:41 +00:00
Cleanups, fixed isValid glitch
This commit is contained in:
@@ -24,7 +24,6 @@ public class Main {
|
||||
|
||||
private static final int DEFAULT_PORT = 8888;
|
||||
|
||||
private static int webserverPort = DEFAULT_PORT;
|
||||
private static boolean ntServerMode = false;
|
||||
private static boolean manageNetwork = true;
|
||||
private static boolean ignoreRoot = false;
|
||||
@@ -43,7 +42,7 @@ public class Main {
|
||||
}
|
||||
}
|
||||
|
||||
public static final Platform CurrentPlatform = Platform.getCurrentPlatform();
|
||||
private static final Platform CurrentPlatform = Platform.getCurrentPlatform();
|
||||
|
||||
private static void handleArgs(String[] args) {
|
||||
for (int i = 0; i < args.length; i++) {
|
||||
@@ -127,12 +126,10 @@ public class Main {
|
||||
|
||||
// Attempt to load the JNI Libraries
|
||||
try {
|
||||
if (CurrentPlatform.equals(Platform.LINUX_ARM64))
|
||||
CameraServerJNI.forceLoad();
|
||||
CameraServerCvJNI.forceLoad();
|
||||
} catch (IOException e) {
|
||||
var errorStr = CurrentPlatform.equals(Platform.UNSUPPORTED) ? "Unsupported platform!" : "Failed to load JNI Libraries!";
|
||||
throw new RuntimeException(errorStr);
|
||||
throw new RuntimeException("Failed to load JNI Libraries!");
|
||||
}
|
||||
|
||||
if (CameraManager.initializeCameras()) {
|
||||
@@ -152,6 +149,7 @@ public class Main {
|
||||
}
|
||||
}
|
||||
|
||||
int webserverPort = DEFAULT_PORT;
|
||||
System.out.printf("Starting Webserver at port %d\n", webserverPort);
|
||||
Server.main(webserverPort);
|
||||
} else {
|
||||
|
||||
@@ -1,22 +1,13 @@
|
||||
package com.chameleonvision.network;
|
||||
|
||||
import com.chameleonvision.settings.NetworkSettings;
|
||||
import com.chameleonvision.settings.SettingsManager;
|
||||
import com.chameleonvision.util.ShellExec;
|
||||
|
||||
import java.io.BufferedOutputStream;
|
||||
import java.io.IOException;
|
||||
import java.net.InetAddress;
|
||||
import java.net.SocketException;
|
||||
import java.net.UnknownHostException;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
|
||||
public class LinuxNetworking extends SysNetworking {
|
||||
|
||||
private ShellExec shell = new ShellExec(true, true);
|
||||
|
||||
@Override
|
||||
public boolean setDHCP() {
|
||||
String[] clearArgs = { "addr", "flush", "dev", networkInterface.name };
|
||||
|
||||
@@ -1,10 +1,8 @@
|
||||
package com.chameleonvision.network;
|
||||
|
||||
import com.chameleonvision.settings.GeneralSettings;
|
||||
|
||||
import java.net.InetAddress;
|
||||
import java.net.InterfaceAddress;
|
||||
|
||||
@SuppressWarnings("WeakerAccess")
|
||||
public class NetworkInterface {
|
||||
public final String name;
|
||||
public final String displayName;
|
||||
@@ -43,9 +41,8 @@ public class NetworkInterface {
|
||||
}
|
||||
// Transform the resulting value in xxx.xxx.xxx.xxx format, like if
|
||||
/// it was a standard address...
|
||||
String maskString = ((shiftby >> 24) & 255) + "." + ((shiftby >> 16) & 255) + "." + ((shiftby >> 8) & 255) + "." + (shiftby & 255);
|
||||
// Return the address thus created...
|
||||
return maskString;
|
||||
// Return the address thus created...
|
||||
return ((shiftby >> 24) & 255) + "." + ((shiftby >> 16) & 255) + "." + ((shiftby >> 8) & 255) + "." + (shiftby & 255);
|
||||
// return InetAddress.getByName(maskString);
|
||||
}
|
||||
catch(Exception e) {
|
||||
|
||||
@@ -1,20 +1,17 @@
|
||||
package com.chameleonvision.network;
|
||||
|
||||
|
||||
import com.chameleonvision.settings.NetworkSettings;
|
||||
import com.chameleonvision.settings.Platform;
|
||||
import com.chameleonvision.settings.SettingsManager;
|
||||
|
||||
import java.net.SocketException;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
|
||||
public class NetworkManager {
|
||||
private NetworkManager() {}
|
||||
|
||||
protected static SysNetworking networking;
|
||||
protected static NetworkInterface botInterface = null;
|
||||
private static SysNetworking networking;
|
||||
private static boolean isManaged = false;
|
||||
|
||||
public static void initialize(boolean manage) {
|
||||
@@ -46,7 +43,7 @@ public class NetworkManager {
|
||||
e.printStackTrace();
|
||||
}
|
||||
|
||||
var teamBytes = NetworkSettings.GetTeamNumberIPBytes(SettingsManager.GeneralSettings.team_number);
|
||||
var teamBytes = NetworkManager.GetTeamNumberIPBytes(SettingsManager.GeneralSettings.team_number);
|
||||
|
||||
if (interfaces.size() > 0) {
|
||||
for (var inetface : interfaces) {
|
||||
@@ -65,7 +62,7 @@ public class NetworkManager {
|
||||
return;
|
||||
}
|
||||
|
||||
botInterface = goodInterfaces.get(0);
|
||||
NetworkInterface botInterface = goodInterfaces.get(0);
|
||||
networking.setNetworkInterface(botInterface);
|
||||
} else {
|
||||
isManaged = false;
|
||||
@@ -79,6 +76,10 @@ public class NetworkManager {
|
||||
}
|
||||
}
|
||||
|
||||
private static byte[] GetTeamNumberIPBytes(int teamNumber) {
|
||||
return new byte[]{(byte) (teamNumber / 100), (byte) (teamNumber % 100)};
|
||||
}
|
||||
|
||||
private static boolean loadFromGeneralSettings() {
|
||||
if (!isManaged) {
|
||||
return true;
|
||||
|
||||
@@ -5,7 +5,6 @@ import com.chameleonvision.util.ShellExec;
|
||||
import java.io.IOException;
|
||||
import java.net.SocketException;
|
||||
import java.util.List;
|
||||
import java.util.Scanner;
|
||||
|
||||
public abstract class SysNetworking {
|
||||
|
||||
|
||||
@@ -1,8 +1,5 @@
|
||||
package com.chameleonvision.network;
|
||||
|
||||
import com.chameleonvision.settings.NetworkSettings;
|
||||
import com.chameleonvision.settings.SettingsManager;
|
||||
|
||||
import java.net.SocketException;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collections;
|
||||
|
||||
@@ -1,80 +0,0 @@
|
||||
package com.chameleonvision.settings;
|
||||
|
||||
import java.net.*;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collections;
|
||||
import java.util.Enumeration;
|
||||
|
||||
import com.chameleonvision.util.Utilities;
|
||||
import org.apache.commons.lang3.StringUtils;
|
||||
import org.apache.commons.lang3.SystemUtils;
|
||||
|
||||
public class NetworkSettings {
|
||||
public String connectionType, ip, netmask, gateway, hostname;
|
||||
|
||||
public void run() {
|
||||
// String adapter = getAdapter();
|
||||
if (SystemUtils.IS_OS_LINUX) {//TODO check linux commands
|
||||
String adapter = getAdapter();
|
||||
if (!adapter.equals("")) {
|
||||
executeCommand("ifconfig " + adapter + " down");
|
||||
if (connectionType.equals("DHCP"))
|
||||
executeCommand("dhclient -r " + adapter);
|
||||
else if (connectionType.equals("Static")) {
|
||||
executeCommand("ifconfig " + adapter + " " + this.ip + " netmask " + this.netmask);
|
||||
executeCommand("route add default gw " + this.gateway + " " + adapter);
|
||||
}
|
||||
executeCommand("ifconfig " + adapter + " up");
|
||||
}
|
||||
executeCommand("hostnamectl set-hostname " + this.hostname);
|
||||
}
|
||||
// //TODO check windows commands
|
||||
// else if (SystemUtils.IS_OS_WINDOWS) {
|
||||
// if (!adapter.equals("")) {
|
||||
// if (connectionType.equals("DHCP")){
|
||||
// executeCommand("cmd /c interface ip set address \"" + adapter + "\" dhcp");
|
||||
// }
|
||||
// else if (connectionType.equals("Static")) {
|
||||
// executeCommand("cmd /c netsh interface ip set address \"" + adapter + "\" static " + this.ip + " " + this.netmask + " " + this.gateway + "1");
|
||||
// }
|
||||
// }
|
||||
// //TODO find a way to change hostname in windows
|
||||
// }
|
||||
}
|
||||
|
||||
private void executeCommand(String command) {
|
||||
try {
|
||||
Process p = Runtime.getRuntime().exec(command);
|
||||
System.out.println("Executing "+ command);
|
||||
p.waitFor();
|
||||
p.destroy();
|
||||
} catch (Exception e) {
|
||||
System.err.println("Error while executing command!");
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
|
||||
public static byte[] GetTeamNumberIPBytes(int teamNumber) {
|
||||
return new byte[]{(byte) (teamNumber / 100), (byte) (teamNumber % 100)};
|
||||
}
|
||||
|
||||
public static String getAdapter() {
|
||||
try {//TODO fix windows get adapter
|
||||
Enumeration<NetworkInterface> nets = NetworkInterface.getNetworkInterfaces();
|
||||
for (NetworkInterface netint : Collections.list(nets)) {
|
||||
Enumeration<InetAddress> ee = netint.getInetAddresses();
|
||||
for (InetAddress addr : Collections.list(ee))
|
||||
if (addr instanceof Inet4Address) {
|
||||
var addrString = addr.toString();
|
||||
if ((addr.getAddress()[0] & 0xFF) == 10 && (addr.getAddress()[1] & 0xFF) == 168) {
|
||||
System.out.println("found robot network interface at " + netint.getName() + " ip: " + addr.getHostAddress());
|
||||
return netint.getName();
|
||||
}
|
||||
}
|
||||
}
|
||||
} catch (SocketException e) {
|
||||
System.err.println("Socket exception while trying to find current IP");
|
||||
}
|
||||
return "";
|
||||
}
|
||||
}
|
||||
@@ -45,7 +45,9 @@ public enum Platform {
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
while (!shell.isOutputCompleted()) {}
|
||||
while (!shell.isOutputCompleted()) {
|
||||
// ignored
|
||||
}
|
||||
if (shell.getExitCode() == 0) {
|
||||
var out = shell.getOutput();
|
||||
out = out.split("\n")[0];
|
||||
|
||||
@@ -1,6 +1,5 @@
|
||||
package com.chameleonvision.settings;
|
||||
|
||||
import com.chameleonvision.network.NetworkManager;
|
||||
import com.chameleonvision.util.FileHelper;
|
||||
import com.chameleonvision.vision.camera.CameraManager;
|
||||
import com.google.gson.Gson;
|
||||
@@ -21,16 +20,6 @@ public class SettingsManager {
|
||||
|
||||
public static void initialize() {
|
||||
initGeneralSettings();
|
||||
// if (manageNetwork) {
|
||||
|
||||
// NetworkSettings netSettings = new NetworkSettings();
|
||||
// netSettings.hostname = GeneralSettings.hostname;
|
||||
// netSettings.gateway = GeneralSettings.gateway;
|
||||
// netSettings.netmask = GeneralSettings.netmask;
|
||||
// netSettings.connectionType = GeneralSettings.connection_type;
|
||||
// netSettings.ip = GeneralSettings.ip;
|
||||
// netSettings.run();
|
||||
// }
|
||||
var allCameras = CameraManager.getAllCamerasByName();
|
||||
if (!allCameras.containsKey(GeneralSettings.curr_camera) && allCameras.size() > 0) {
|
||||
var cam = allCameras.entrySet().stream().findFirst().get().getValue();
|
||||
|
||||
@@ -101,7 +101,7 @@ public class ShellExec {
|
||||
* http://www.javaworld.com/javaworld/jw-12-2000/jw-1229-traps.html?page=4
|
||||
*/
|
||||
@SuppressWarnings("WeakerAccess")
|
||||
private class StreamGobbler extends Thread {
|
||||
private static class StreamGobbler extends Thread {
|
||||
private InputStream is;
|
||||
private StringBuilder output;
|
||||
private volatile boolean completed; // mark volatile to guarantee a thread safety
|
||||
|
||||
@@ -26,7 +26,7 @@ public class Utilities {
|
||||
}
|
||||
|
||||
public static List<Integer> getDigits(int num) {
|
||||
List<Integer> digits = new ArrayList<Integer>();
|
||||
List<Integer> digits = new ArrayList<>();
|
||||
collectDigits(num, digits);
|
||||
return digits;
|
||||
}
|
||||
|
||||
@@ -70,14 +70,13 @@ public class CVProcess {
|
||||
}
|
||||
var rect = Imgproc.minAreaRect(new MatOfPoint2f(Contour.toArray()));
|
||||
|
||||
var targetFullness = contourArea;
|
||||
double minExtent = (double) (extent.get(0) * rect.size.area()) / 100;
|
||||
double maxExtent = (double) (extent.get(1) * rect.size.area()) / 100;
|
||||
if (targetFullness <= minExtent || contourArea >= maxExtent) {
|
||||
double minExtent = (extent.get(0) * rect.size.area()) / 100;
|
||||
double maxExtent = (extent.get(1) * rect.size.area()) / 100;
|
||||
if (contourArea <= minExtent || contourArea >= maxExtent) {
|
||||
continue;
|
||||
}
|
||||
Rect bb = Imgproc.boundingRect(Contour);
|
||||
double aspectRatio = (bb.width / bb.height);
|
||||
double aspectRatio = ((double)bb.width / bb.height);
|
||||
if (aspectRatio < ratio.get(0) || aspectRatio > ratio.get(1)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
@@ -2,12 +2,33 @@ package com.chameleonvision.vision.process;
|
||||
|
||||
import org.opencv.core.RotatedRect;
|
||||
|
||||
@SuppressWarnings("WeakerAccess")
|
||||
public class PipelineResult {
|
||||
public boolean IsValid = false;
|
||||
public double CalibratedX = 0.0;
|
||||
public double CalibratedY = 0.0;
|
||||
public double Pitch = 0.0;
|
||||
public double Yaw = 0.0;
|
||||
public double Area = 0.0;
|
||||
RotatedRect RawPoint;
|
||||
public final boolean IsValid;
|
||||
public final double CalibratedX;
|
||||
public final double CalibratedY;
|
||||
public final double Pitch;
|
||||
public final double Yaw;
|
||||
public final double Area;
|
||||
public final RotatedRect RawPoint;
|
||||
|
||||
public PipelineResult() {
|
||||
IsValid = false;
|
||||
CalibratedX = 0.0;
|
||||
CalibratedY = 0.0;
|
||||
Pitch = 0.0;
|
||||
Yaw = 0.0;
|
||||
Area = 0.0;
|
||||
RawPoint = new RotatedRect();
|
||||
}
|
||||
|
||||
public PipelineResult(double calX, double calY, double pitch, double yaw, double area, RotatedRect rawPoint) {
|
||||
IsValid = true;
|
||||
CalibratedX = calX;
|
||||
CalibratedY = calY;
|
||||
Pitch = pitch;
|
||||
Yaw = yaw;
|
||||
Area = area;
|
||||
RawPoint = rawPoint;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -20,7 +20,7 @@ public class VisionProcess implements Runnable {
|
||||
private final CameraProcess cameraProcess;
|
||||
// NetworkTables
|
||||
public NetworkTableEntry ntPipelineEntry;
|
||||
public NetworkTableEntry ntDriverModeEntry;
|
||||
private NetworkTableEntry ntDriverModeEntry;
|
||||
private NetworkTableEntry ntYawEntry;
|
||||
private NetworkTableEntry ntPitchEntry;
|
||||
private NetworkTableEntry ntDistanceEntry;
|
||||
@@ -112,7 +112,11 @@ public class VisionProcess implements Runnable {
|
||||
Imgproc.rectangle(inputMat,new Point(box.x, box.y), new Point((box.x + box.width),(box.y + box.height)), BoxRectColor,2);
|
||||
}
|
||||
|
||||
private boolean wasValid = false;
|
||||
|
||||
private void updateNetworkTables(PipelineResult pipelineResult) {
|
||||
boolean isValid = pipelineResult.IsValid;
|
||||
|
||||
if (pipelineResult.IsValid) {
|
||||
ntValidEntry.setBoolean(true);
|
||||
ntYawEntry.setNumber(pipelineResult.Yaw);
|
||||
@@ -127,20 +131,25 @@ public class VisionProcess implements Runnable {
|
||||
ntTimeStampEntry.setNumber(timeStamp);
|
||||
ntValidEntry.setBoolean(false);
|
||||
}
|
||||
// on validity state change, force a flush
|
||||
if (isValid != wasValid) {
|
||||
// System.out.printf("Validity changed from %b to %b\n", wasValid, isValid);
|
||||
NetworkTableInstance.getDefault().flush();
|
||||
wasValid = isValid;
|
||||
}
|
||||
}
|
||||
|
||||
private PipelineResult runVisionProcess(Mat inputImage, Mat outputImage) {
|
||||
var pipelineResult = new PipelineResult();
|
||||
|
||||
if (currentPipeline == null) {
|
||||
return pipelineResult;
|
||||
return new PipelineResult();
|
||||
}
|
||||
if (!currentPipeline.orientation.equals("Normal")) {
|
||||
Core.flip(inputImage, inputImage, -1);
|
||||
}
|
||||
if (ntDriverModeEntry.getBoolean(false)) {
|
||||
inputImage.copyTo(outputImage);
|
||||
return pipelineResult;
|
||||
return new PipelineResult();
|
||||
}
|
||||
Scalar hsvLower = new Scalar(currentPipeline.hue.get(0), currentPipeline.saturation.get(0), currentPipeline.value.get(0));
|
||||
Scalar hsvUpper = new Scalar(currentPipeline.hue.get(1), currentPipeline.saturation.get(1), currentPipeline.value.get(1));
|
||||
@@ -159,25 +168,25 @@ public class VisionProcess implements Runnable {
|
||||
groupedContours = cvProcess.groupTargets(filteredContours, currentPipeline.target_intersection, currentPipeline.target_group);
|
||||
if (groupedContours.size() > 0) {
|
||||
var finalRect = cvProcess.sortTargetsToOne(groupedContours, currentPipeline.sort_mode);
|
||||
// System.out.printf("Largest Contour Area: %.2f\n", finalRect.size.area());
|
||||
pipelineResult.RawPoint = finalRect;
|
||||
pipelineResult.IsValid = true;
|
||||
double calX, calY;
|
||||
|
||||
if (!currentPipeline.is_calibrated) {
|
||||
pipelineResult.CalibratedX = camera.getCamVals().CenterX;
|
||||
pipelineResult.CalibratedY = camera.getCamVals().CenterY;
|
||||
calX = camera.getCamVals().CenterX;
|
||||
calY = camera.getCamVals().CenterY;
|
||||
} else {
|
||||
pipelineResult.CalibratedX = (finalRect.center.y - currentPipeline.B) / currentPipeline.M;
|
||||
pipelineResult.CalibratedY = (finalRect.center.x * currentPipeline.M) + currentPipeline.B;
|
||||
calX = (finalRect.center.y - currentPipeline.B) / currentPipeline.M;
|
||||
calY = (finalRect.center.x * currentPipeline.M) + currentPipeline.B;
|
||||
}
|
||||
pipelineResult.Pitch = camera.getCamVals().CalculatePitch(finalRect.center.y, pipelineResult.CalibratedY);
|
||||
pipelineResult.Yaw = camera.getCamVals().CalculateYaw(finalRect.center.x, pipelineResult.CalibratedX);
|
||||
pipelineResult.Area = finalRect.size.area();
|
||||
var pitch = camera.getCamVals().CalculatePitch(finalRect.center.y, calY);
|
||||
var yaw = camera.getCamVals().CalculateYaw(finalRect.center.x, calX);
|
||||
var area = finalRect.size.area();
|
||||
drawContour(outputImage, finalRect);
|
||||
return new PipelineResult(calX, calY, pitch, yaw, area, finalRect);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return pipelineResult;
|
||||
return new PipelineResult();
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -13,10 +13,7 @@ import org.json.JSONObject;
|
||||
import org.springframework.beans.BeanUtils;
|
||||
|
||||
import java.lang.reflect.Field;
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.*;
|
||||
|
||||
public class ServerHandler {
|
||||
|
||||
@@ -175,7 +172,7 @@ public class ServerHandler {
|
||||
map.put(field.getName(), field.get(obj));
|
||||
}
|
||||
} catch (IllegalAccessException e) {
|
||||
System.err.println("Illegal Access error:" + e.getStackTrace());
|
||||
System.err.println("Illegal Access error:" + Arrays.toString(e.getStackTrace()));
|
||||
}
|
||||
return map;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user