Commit 8667ae4b authored by Andrey Filippov's avatar Andrey Filippov

Object matching in different flights

parent 02845a72
......@@ -849,6 +849,7 @@ public class Eyesis_Correction implements PlugIn, ActionListener {
addButton("Read Tiff", panelLWIRWorld, color_process);
addButton("Test video", panelLWIRWorld, color_process);
addButton("Ortho Pairs", panelLWIRWorld, color_process);
addButton("Extract Objects", panelLWIRWorld, color_process);
addButton("Mismatched resolutions", panelLWIRWorld, color_process);
addButton("Generate DATI", panelLWIRWorld, color_process);
addButton("Create mine", panelLWIRWorld, color_process);
......@@ -5708,7 +5709,7 @@ public class Eyesis_Correction implements PlugIn, ActionListener {
e.printStackTrace();
}
// ComboMatch.testReadTiff();
} else if (label.equals("Ortho Pairs")) {
} else if (label.equals("Ortho Pairs") || label.equals("Extract Objects")) {
DEBUG_LEVEL = MASTER_DEBUG_LEVEL;
EYESIS_CORRECTIONS.setDebug(DEBUG_LEVEL);
if (GPU_TILE_PROCESSOR == null) {
......@@ -5729,6 +5730,7 @@ public class Eyesis_Correction implements PlugIn, ActionListener {
ComboMatch.openTestPairGps(
CLT_PARAMETERS, // CLTParameters clt_parameters,
GPU_TILE_PROCESSOR,
label.equals("Extract Objects"), // boolean extract_mines,
DEBUG_LEVEL);
} else if (label.equals("Test video")) {
ImagePlus imp_sel = WindowManager.getCurrentImage();
......
package com.elphel.imagej.orthomosaic;
import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.io.Serializable;
import java.util.ArrayList;
import ij.Prefs;
public class AltitudeMismatchKernel implements Serializable{
private static final long serialVersionUID = 1L;
public static String kernels_directory;
public int zoom_level;
public double agl_from;
public double agl_to;
public String filename;
public AltitudeMismatchKernel (
String filename,
int zoom_level,
double agl_from,
double agl_to) {
this.filename = filename;
this.zoom_level = zoom_level;
this.agl_from = agl_from;
this.agl_to = agl_to;
}
private void writeObject(ObjectOutputStream oos) throws IOException {
oos.defaultWriteObject();
}
private void readObject(ObjectInputStream ois) throws ClassNotFoundException, IOException {
ois.defaultReadObject();
}
public static void setKernelsDirectory(
String directory) {
while (directory.endsWith(Prefs.getFileSeparator())){
directory=directory.substring(0, directory.length()-1);
}
kernels_directory = directory;
}
public static String getKernelsDirectory() {
return kernels_directory;
}
public String getKernelPath() {
return kernels_directory+Prefs.getFileSeparator()+filename;
}
public static AltitudeMismatchKernel getKernel(
int zoom_level,
double agl_from,
double agl_to,
ArrayList<AltitudeMismatchKernel> kernels) {
double tolerance = 0.15;
double agl_from_min = agl_from * (1.0 - tolerance);
double agl_from_max = agl_from * (1.0 + tolerance);
double agl_to_min = agl_to * (1.0 - tolerance);
double agl_to_max = agl_to * (1.0 + tolerance);
for (AltitudeMismatchKernel kernel:kernels) {
if (zoom_level == kernel.zoom_level) {
if ( (kernel.agl_from >= agl_from_min) &&
(kernel.agl_from <= agl_from_max) &&
(kernel.agl_to >= agl_to_min) &&
(kernel.agl_to <= agl_to_max))
return kernel;
}
}
return null;
}
}
......@@ -46,6 +46,7 @@ public class ComboMatch {
public static boolean openTestPairGps(
CLTParameters clt_parameters,
GPUTileProcessor gpu_tile_processor, // initialized by the caller
boolean extract_mines,
int debugLevel) {
GPU_TILE_PROCESSOR = gpu_tile_processor;
PairwiseOrthoMatch pairwiseOrthoMatch = null;
......@@ -85,11 +86,13 @@ public class ComboMatch {
// String files_list_path = "/media/elphel/SSD3-4GB/lwir16-proc/ortho_videos/maps_19_sep13_25-50-75-100m.list";
// String orthoMapsCollection_path = "/media/elphel/SSD3-4GB/lwir16-proc/ortho_videos/maps_19_sep13_25-50-75-100m.data";
String [] files_lists_paths = {
"/media/elphel/SSD3-4GB/lwir16-proc/ortho_videos/maps_sep12-13_50-25-50-75-100m",
"/media/elphel/SSD3-4GB/lwir16-proc/ortho_videos/maps_19_sep13_25-50-75-100m",
"/media/elphel/SSD3-4GB/lwir16-proc/ortho_videos/maps_nov3_50-75"};
"/media/elphel/SSD3-4GB/lwir16-proc/ortho_videos/maps_nov3_50-75",
"/media/elphel/SSD3-4GB/lwir16-proc/ortho_videos/maps_sep12-50m"};
String files_list_path = "/media/elphel/SSD3-4GB/lwir16-proc/ortho_videos/maps_nov3_50-75.list";
String orthoMapsCollection_path = "/media/elphel/SSD3-4GB/lwir16-proc/ortho_videos/maps_nov3_50-75.data";
// String files_list_path = "/media/elphel/SSD3-4GB/lwir16-proc/ortho_videos/maps_nov3_50-75.list";
// String orthoMapsCollection_path = "/media/elphel/SSD3-4GB/lwir16-proc/ortho_videos/maps_nov3_50-75.data";
//maps_nov3_50-75
//maps_19_sep13.list
//maps_09_short.list
......@@ -133,10 +136,16 @@ public class ComboMatch {
boolean process_correlation = true; // use false to save new version of data
boolean update_match = true; // use false to save new version of data
boolean render_match = true;
boolean restore_temp = true;
boolean pattern_match = false;
boolean bounds_to_indices = true;
int temp_mode = 1;
boolean restore_temp = true;
double frac_remove = 0.15;
double metric_error = 0.05; // 0.02;// 2 cm
boolean update_lla = false; // re-read file metadata
boolean update_kernel_patterns = false;
if (!use_marked_image) {
process_correlation=false; // use already adjusted by default
}
......@@ -149,6 +158,13 @@ public class ComboMatch {
gd.addCheckbox ("Process correlations", process_correlation, "false to skip to just regenerate new save file.");
gd.addCheckbox ("Update match if calculated", update_match, "Will update correlation match for a pair if found.");
gd.addCheckbox ("Render match", render_match, "Render a pair of matched images.");
gd.addCheckbox ("Pattern match", pattern_match, "Search for patterns for both images in a pair, first is primary.");
gd.addCheckbox ("Bounds to selected images", bounds_to_indices, "Set combo image bounds to selected images only. False - all images.");
gd.addNumericField("Temp mode", temp_mode, 0,4,"",
"O - do not modify average pixels, 1 - equalize second image to first, 2 - try to account for raw average");
//temp_mode
/*
for (int n = 0; n < image_enuatr.length; n++) {
gd.addMessage("image["+n+"] pose");
......@@ -174,18 +190,24 @@ public class ComboMatch {
if (use_marked_image ) {
gd.addCheckbox ("Use marked image data", true, "Use markes from the selected image");
}
gd.addCheckbox ("Update files metadata", update_lla, "Re-read files metadata (ifd it was modified)");
gd.addCheckbox ("Update files metadata", update_lla, "Re-read files metadata (if it was modified)");
gd.addCheckbox ("Update kernels/patterns", update_kernel_patterns, "Re-read kernels and patterns from *.list file");
// update_kernel_patterns
gd.showDialog();
if (gd.wasCanceled()) return false;
int choice_index = gd.getNextChoiceIndex();
files_list_path = files_lists_paths[choice_index]+".list";
orthoMapsCollection_path =files_lists_paths[choice_index]+".data";
String files_list_path = files_lists_paths[choice_index]+".list";
String orthoMapsCollection_path =files_lists_paths[choice_index]+".data";
use_saved_collection = gd.getNextBoolean();
save_collection = gd.getNextBoolean();
process_correlation= gd.getNextBoolean();
update_match= gd.getNextBoolean();
render_match= gd.getNextBoolean();
pattern_match= gd.getNextBoolean();
bounds_to_indices= gd.getNextBoolean();
temp_mode = (int) gd.getNextNumber();
/*
for (int n = 0; n < image_enuatr.length; n++) {
image_enuatr[n][0][0] = gd.getNextNumber();
......@@ -214,6 +236,7 @@ public class ComboMatch {
use_marked_image= gd.getNextBoolean();
}
update_lla= gd.getNextBoolean();
update_kernel_patterns= gd.getNextBoolean();
OrthoMapsCollection maps_collection=null;
if (use_saved_collection) {
try {
......@@ -222,6 +245,11 @@ public class ComboMatch {
// TODO Auto-generated catch block
e.printStackTrace();
}
//files_list_path
if (update_kernel_patterns) {
maps_collection.updateKernels(files_list_path);
maps_collection.updatePatterns(files_list_path);
}
} else {
maps_collection = new OrthoMapsCollection(files_list_path); // should have ".list" extension
}
......@@ -266,6 +294,7 @@ public class ComboMatch {
false, // boolean use_alt,
show_centers, // boolean show_centers,
zoom_lev, // int zoom_level,
temp_mode, // int temp_mode, // 0 - do nothing, 1 - equalize average,2 - try to correct
origin); // int [] origin){
imp_img.show();
}
......@@ -273,13 +302,14 @@ public class ComboMatch {
if (use_alt) {
imp_alt =maps_collection.renderMulti (
"multi_alt_zoom"+zoom_lev, // String title,
true, // boolean use_alt,
true, // boolean use_alt,
show_centers, // boolean show_centers,
zoom_lev, // int zoom_level,
0, // int temp_mode, // 0 - do nothing, 1 - equalize average,2 - try to correct
origin); // int [] origin){
imp_alt.show();
}
if (process_correlation || render_match ) {
if (process_correlation || render_match || pattern_match) {
// int [] gpu_pair;
if (gpu_spair == null) {
ArrayList<Point> pairs_list = new ArrayList<Point>();
......@@ -409,40 +439,26 @@ public class ComboMatch {
System.out.println();
}
}
if (pattern_match) {
ImagePlus imp_pat_match = maps_collection.patterMatchDualWrap (
gpu_pair, // int [] indices, // null or which indices to use (normally just 2 for pairwise comparison)
affines, // double [][][] affines, // null or [indices.length][2][3]
warp); // FineXYCorr warp)
// imp_pat_match.show();
}
if (render_match) {
ImagePlus imp_img_pair = maps_collection.renderMulti (
"multi_"+gpu_spair[0]+"-"+gpu_spair[1]+"-zoom_"+min_zoom_lev+"_"+zoom_lev, // String title,
false, // boolean use_alt,
gpu_pair, // int [] indices, // null or which indices to use (normally just 2 for pairwise comparison)
bounds_to_indices, // boolean bounds_to_indices,
temp_mode, // int temp_mode, // 0 - do nothing, 1 - equalize average,2 - try to correct
affines, // double [][][] affines, // null or [indices.length][2][3]
warp, // FineXYCorr warp,
show_centers, // boolean show_centers,
min_zoom_lev, // int zoom_level,
origin); // int [] origin){
imp_img_pair.show();
/*
int gpu_tilesX = gpu_width/GPUTileProcessor.DTT_SIZE;
Rectangle tile_woi = OrthoMapsCollection.scaleRectangle (woi, GPUTileProcessor.DTT_SIZE);
double [][] vector_field_interpolated = interpolateVectorField(
vector_field, // final double [][] vector_field, // sparse {vx,vy,strength}
gpu_tilesX, // final int gpu_tilesX, // 512
tile_woi, // final Rectangle tile_woi, // only width, height are used top-left corners are the same
scale, // final double scale,
1); // final int debugLevel);
ImagePlus imp_img_pair = maps_collection.renderMulti (
"multi_"+gpu_spair[0]+"-"+gpu_spair[1]+"-zoom_"+min_zoom_lev+"_"+zoom_lev, // String title,
false, // boolean use_alt,
gpu_pair, // int [] indices, // null or which indices to use (normally just 2 for pairwise comparison)
affines, // double [][][] affines, // null or [indices.length][2][3]
show_centers, // boolean show_centers,
min_zoom_lev, // int zoom_level,
origin); // int [] origin){
imp_img_pair.show();
*/
imp_img_pair.show();
}
}
}
......
......@@ -5,6 +5,7 @@ import java.awt.Rectangle;
import com.elphel.imagej.gpu.GPUTileProcessor;
public class FineXYCorr {
public double scale_warp = 1.0;
public double [] top_left_metric; // relative to the reference image vertical point, normally negative
public int width_tiles;
public int height_tiles;
......@@ -60,7 +61,7 @@ public class FineXYCorr {
* Apply warping to the x,y pair
* @param xy {X,Y} before and after warping
*/
public void warpXY(// in render pixels
public void warpXY(// in render pixels NOT_USED
double [] xy) { // no interpolation - using nearest
int ix = (int) Math.round((xy[0] - render_tl[0]) * render_div_tile);
int iy = (int) Math.round((xy[1] - render_tl[1]) * render_div_tile);
......@@ -82,8 +83,8 @@ public class FineXYCorr {
double [] dxdy = warp_xy[ix + width_tiles * iy];
if (dxdy != null) {
return new double [] {
dxdy[0]*pix_div_render,
dxdy[1]*pix_div_render};
dxdy[0]*pix_div_render*scale_warp,
dxdy[1]*pix_div_render*scale_warp};
}
}
return new double [2];
......
package com.elphel.imagej.orthomosaic;
import java.io.IOException;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.io.Serializable;
import java.time.LocalDateTime;
import java.util.ArrayList;
import ij.Prefs;
public class GroundObjectPattern implements Serializable {
private static final long serialVersionUID = 1L;
public static long UTC_EAST_HRS = 3;
public static String patterns_directory;
//public LocalDateTime plusHours(long hours)
public int zoom_level; // 1 for 5mm/pix
public String object_type; // like "TM62"
// public String object_version; // just change config
LocalDateTime utcDateTime; // UTC
public String filename; // should be square
public GroundObjectPattern(
String filename,
int zoom_level,
String object_type,
LocalDateTime utcDateTime) {
this.filename = filename;
this.zoom_level = zoom_level;
this.object_type = object_type;
this.utcDateTime = utcDateTime;
}
private void writeObject(ObjectOutputStream oos) throws IOException {
oos.defaultWriteObject();
}
private void readObject(ObjectInputStream ois) throws ClassNotFoundException, IOException {
ois.defaultReadObject();
}
public static void setPatternsDirectory(
String directory) {
while (directory.endsWith(Prefs.getFileSeparator())){
directory=directory.substring(0, directory.length()-1);
}
patterns_directory = directory;
}
public String getPatternPath() {
return patterns_directory+Prefs.getFileSeparator()+filename;
}
public static String getPatternsDirectory() {
return patterns_directory;
}
public static GroundObjectPattern getPattern(
String object_type,
LocalDateTime utcDateTime,
ArrayList<GroundObjectPattern> patterns) {
GroundObjectPattern best_gop = null;
long best_hrs_diff = 24;
for (GroundObjectPattern gop:patterns) {
if ((object_type == null) || object_type.equals(gop.object_type)) {
if (utcDateTime != null) {
long hrs_diff = Math.abs(utcDateTime.getHour()-gop.utcDateTime.getHour());
if (hrs_diff > 12) {
hrs_diff = 24 -hrs_diff;
}
if (hrs_diff < best_hrs_diff) {
best_gop = gop;
best_hrs_diff = hrs_diff;
}
} else {
best_gop = gop; // use latest
}
}
}
return best_gop;
}
public LocalDateTime getUTC() {
return utcDateTime;
}
public LocalDateTime getLocalDT() {
return utcDateTime.plusHours(UTC_EAST_HRS);
}
public boolean isEvening() {
return getLocalDT().getHour() >= 12;
}
public double getAGL() {
double agl = 50; // zoom 0 for 50m AGL
for (int z = zoom_level; z > 0; z--) {
agl /=2;
}
for (int z = zoom_level; z < 0; z++) {
agl *=2;
}
return agl;
}
public int getZoomLevel() {
return zoom_level;
}
}
package com.elphel.imagej.orthomosaic;
public class ObjectLocation {
String name;
double [] xy_meters;
}
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment