Skip to content

Commit 8ccca38

Browse files
author
Erika
committed
added functions for pointCloud and integrated camera
1 parent b46eea3 commit 8ccca38

File tree

3 files changed

+202
-46
lines changed

3 files changed

+202
-46
lines changed

depthmap/depthmap.cpp

+163-31
Original file line numberDiff line numberDiff line change
@@ -698,55 +698,56 @@ void Depthmap::resizeNormals (int factorPowerOfTwo, int step) {
698698
//depthIntegrateNormals();
699699

700700
}
701-
void Depthmap::loadPointCloud(const char *textPath, std::vector<float> &points){
702701

703-
//apri file di testo e scarta tutto quello che non è un numero. fai un char vettore di punti
704-
QFile file(textPath);
705-
if (!file.open(QIODevice::ReadOnly | QIODevice::Text)) {
706-
throw QString("Error opening input file: ")+ textPath;
707-
}
708702

709-
QTextStream in(&file);
703+
/*
710704
711-
while (!in.atEnd()) {
712-
QString line = in.readLine().trimmed();
713-
QStringList parts = line.split(QRegularExpression("\\s+"), Qt::SkipEmptyParts);
714-
if (line.isEmpty() || (!line[0].isDigit() && line[0] != '-' && line[0] != '+') || parts.size() != 6) {
715-
continue;
716-
}
705+
void Depthmap::depth(const char *depth_path){
706+
std::vector<float> depthValues;
707+
if (!load(depth_path)) {
708+
cerr << "Failed to load depth map." << endl;
709+
return;
710+
}
711+
for (size_t i = 0; i < depthValues.size(); i++) {
712+
float realX = depthValues[i];
713+
float realY = depthValues[++i];
714+
float realZ = depthValues[++i];
717715
718-
//check the line if the line not begin with float number break
719-
bool isValid = true;
720-
float v[3];
721-
for (int i = 0; i < 3; ++i) {
722-
bool isNumber = false;
723-
v[i] = parts[i].toFloat(&isNumber);
724-
if (!isNumber) {
725-
isValid = false;
726-
break;
727-
}
728-
}
729-
if (!isValid)
730-
throw QString("Invalide ply");
716+
Eigen::Vector3f pixelCoords = realToPixelCoord(realX, realY, realZ);
717+
int pixelX = pixelCoords[0];
718+
int pixelY = pixelCoords[1];
719+
float calcZ = pixelCoords[2];
720+
721+
Eigen::Vector3f = projectToCameraDepthMap(pixelCoord);
731722
732-
for (int i = 0; i < 3; ++i){
733-
points.push_back(v[i]);
734-
}
735723
}
736724
737725
}
738726
739727
//funzione inversa da 3d a xyh; xy z=0 h? pixel,pixel, h
740-
void Depthmap::t3DToCamera(P){
728+
void Depthmap::t3DToCamera(float h, ){
741729
//xyz coord 3d fai l'inversa: aperi txt, x e y. prendi funz 3d la trosformi in x y e h e poi applichi quella già fatta camerato3d e deve venire uguale
742730
//poi prendi apericloud e vedi se coincide con la depth
743731
//2. scrivi la funzione inversa da un punto in 3d ci trova la x e la y in pixel e la h dalla depth del mic mac
744732
//3. verifica se la h trovata per i punti di aperi corrisponde all h della depth map
745733
734+
for (size_t i = 0; i < points.size(); i += 3) {
735+
float realX = points[i];
736+
float realY = points[i + 1];
737+
float realZ = points[i + 2];
746738
747-
}
739+
Eigen::Vector3f pixelCoords = realToPixelCoordinates(realX, realY, realZ);
740+
741+
int pixelX = pixelCoords[0];
742+
int pixelY = pixelCoords[1];
743+
float calcZ = pixelCoords[2];
748744
749745
746+
float invH= (h - origin[2]) / resolution[2];
747+
}
748+
}
749+
750+
*/
750751
//take the x=160,14 e y=140
751752
//the coordinates of the pixel step 0.016 are in the depth map xml Z_num etc.
752753

@@ -897,14 +898,145 @@ void OrthoDepthmap::projectToCameraDepthMap(const Camera& camera, const QString&
897898
}
898899
depthMapImage.save(outputPath, "png");
899900
}
901+
900902
void OrthoDepthmap::resizeNormals (int factorPowerOfTwo, int step) {
901903
int factor = 1 << factorPowerOfTwo;
902904
Depthmap::resizeNormals(factorPowerOfTwo, step);
903905
resolution *= factor;
904906
origin /= factor;
905907
}
906908

909+
void OrthoDepthmap::loadPointCloud(const char *textPath){
907910

911+
//apri file di testo e scarta tutto quello che non è un numero. fai un char vettore di punti
912+
QFile file(textPath);
913+
if (!file.open(QIODevice::ReadOnly | QIODevice::Text)) {
914+
throw QString("Error opening input file: ")+ textPath;
915+
}
916+
917+
QTextStream in(&file);
918+
919+
920+
while (!in.atEnd()) {
921+
QString line = in.readLine().trimmed();
922+
QStringList parts = line.split(QRegularExpression("\\s+"), Qt::SkipEmptyParts);
923+
if (line.isEmpty() || (!line[0].isDigit() && line[0] != '-' && line[0] != '+') || parts.size() != 6) {
924+
continue;
925+
}
926+
927+
//check the line if the line not begin with float number break
928+
bool isValid = true;
929+
Eigen::Vector3f v;
930+
for (int i = 0; i < 3; ++i) {
931+
bool isNumber = false;
932+
v[i] = parts[i].toFloat(&isNumber);
933+
if (!isNumber) {
934+
isValid = false;
935+
break;
936+
}
937+
}
938+
if (!isValid)
939+
throw QString("Invalide ply");
940+
941+
point_cloud.push_back(v);
942+
943+
}
944+
945+
946+
}
947+
948+
Eigen::Vector3f OrthoDepthmap::realToPixelCoord(float realX, float realY, float realZ){
949+
float pixelX = (realX - origin[0]) / resolution[0];
950+
float pixelY = (realY - origin[1]) / resolution[1];
951+
float h = (realZ - origin[2]) / resolution[2];
952+
return Eigen::Vector3f(pixelX, pixelY, h);
953+
954+
}
955+
956+
void OrthoDepthmap::verifyPointCloud(){
957+
958+
for(const auto& point : point_cloud){
959+
960+
float realX = point[0];
961+
float realY = point[1];
962+
float realZ = point[2];
963+
964+
Eigen::Vector3f pixelCoord = realToPixelCoord(realX, realY, realZ);
965+
966+
Eigen::Vector3f realCoord = pixelToRealCoordinates(pixelCoord[0], pixelCoord[1], pixelCoord[2]);
967+
968+
969+
// int pixelX = static_cast<int>(round(pixelCoord[0]));
970+
// int pixelY = static_cast<int>(round(pixelCoord[1]));
971+
972+
int pixelX = static_cast<int>(round(pixelCoord[0]));
973+
int pixelY = static_cast<int>(round(pixelCoord[1]));
974+
975+
if (pixelX < 0 || pixelX >= width || pixelY < 0 || pixelY >= height) {
976+
continue;
977+
}
978+
cerr << "point inside the image limits "
979+
<< "Point 3D: (" << realX << ", " << realY << ", " << pixelCoord[2] << "), "
980+
<< "Coordinate pixel: (" << pixelX << ", " << pixelY << " " << elevation[pixelX + pixelY * width]<< ")\n";
981+
982+
}
983+
984+
985+
}
986+
void OrthoDepthmap::integratedCamera(const CameraDepthmap& camera){
987+
int count =0;
988+
for (size_t i = 0; i < point_cloud.size(); i++) {
989+
990+
Eigen::Vector3f& realCoord = point_cloud[i];
991+
Eigen::Vector3f imageCoords = camera.camera.projectionToImage(realCoord);
992+
Eigen::Vector3f pixelCoord = realToPixelCoord(realCoord[0], realCoord[1], realCoord[2]);
993+
994+
int pixelX = static_cast<int>(round(imageCoords[0]));
995+
int pixelY = static_cast<int>(round(imageCoords[1]));
996+
997+
if (pixelX >= 0 && pixelX < camera.width && pixelY >= 0 && pixelY < camera.height) {
998+
float depthValue = elevation[pixelX + pixelY * camera.width];
999+
float h = pixelCoord[2];
1000+
count++;
1001+
cout << depthValue << h << endl;
1002+
1003+
1004+
}
1005+
}
1006+
cout << count << endl;
1007+
}
1008+
//fit h = a+b*elev
1009+
1010+
void OrthoDepthmap::fitLinearRegressionFromPairs() {
1011+
float sumElevation = 0; // Somma delle elevazioni (x)
1012+
float sumH = 0; // Somma dei valori h (y)
1013+
float sumElevationH = 0; // Somma delle moltiplicazioni elevation * h
1014+
float sumElevationSquared = 0; // Somma delle elevazioni al quadrato
1015+
size_t n = point_cloud.size(); // Numero di punti nella nuvola di punti
1016+
1017+
// Ciclo sui punti per raccogliere i dati
1018+
for (const auto& point : point_cloud) {
1019+
float elevation = point[0]; // Elevation (x)
1020+
float h = point[2]; // Altezza (y)
1021+
1022+
sumElevation += elevation;
1023+
sumH += h;
1024+
sumElevationH += elevation * h;
1025+
sumElevationSquared += elevation * elevation;
1026+
}
1027+
1028+
float b = (n * sumElevationH - sumElevation * sumH) / (n * sumElevationSquared - sumElevation * sumElevation);
1029+
float a = (sumH - b * sumElevation) / n;
1030+
1031+
for (const auto& point : point_cloud) {
1032+
float elevation = point[0];
1033+
float hCalculated = a + b * elevation;
1034+
cout << "For elevation:" << elevation << "calculated h:" << hCalculated << endl;
1035+
}
1036+
1037+
}
1038+
//Real to Pixel Coordinates: (-0.981, 2.041, -11.132) -> Pixel: (110.688, 65.4375, -27.75)
1039+
//point outside the image limits Point 3D: (-0.981, 2.041, -11.132), Coordinate pixel: (-1, 2)
9081040

9091041

9101042
/* ---------------------------------------------------------------------------------------------------------------------------*/

depthmap/depthmap.h

+13-1
Original file line numberDiff line numberDiff line change
@@ -41,7 +41,6 @@ class Depthmap {
4141
bool loadDepth(const char *depth_path);
4242
bool loadMask(const char *mask_path);
4343
bool loadNormals(const char *normals_path);
44-
bool loadText(const char *textPath, const char *outputPath);
4544
void saveDepth(const char *depth_path);
4645
void saveMask(const char *depth_path);
4746
void saveNormals(const char *normals_path);
@@ -65,6 +64,7 @@ class CameraDepthmap:
6564
public Depthmap {
6665
public:
6766
Camera camera;
67+
6868
/*1. load tif filename, convertita in vector3f
6969
*
7070
*/
@@ -75,13 +75,25 @@ class OrthoDepthmap:
7575
public:
7676
Eigen::Vector3f resolution;
7777
Eigen::Vector3f origin;
78+
std::vector<Eigen::Vector3f> point_cloud;
79+
7880

7981
Eigen::Vector3f pixelToRealCoordinates(int pixelX, int pixelY, float pixelZ);
82+
Eigen::Vector3f realToPixelCoord(float realX, float realY, float realZ);
8083
bool load(const char *depth_path, const char *mask_path);
8184
bool loadXml(const char *xmlPath);
8285
void saveObj(const char *filename);
8386
void projectToCameraDepthMap(const Camera& camera, const QString& outputPath);
8487
void resizeNormals(int factorPowerOfTwo, int step = 1);
88+
void loadPointCloud(const char *textPath);
89+
//itera sui punti, chiama l'inversa, prima converte a intero perche sono float vede se xy stanno in w e h, se non dentro problema
90+
//legge nella depth l h corrispondente
91+
void verifyPointCloud();
92+
void integratedCamera(const CameraDepthmap& camera);
93+
void fitLinearRegressionFromPairs();
94+
95+
96+
8597

8698

8799
/*1.

depthmap/main.cpp

+26-14
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,7 @@ int main(int argc, char *argv[]) {
1414
return 1;
1515
}*/
1616
//input
17-
//#define MACOS 1
17+
#define MACOS 1
1818
#ifdef MACOS
1919
QString base = "/Users/erika/Desktop/";
2020
#else
@@ -24,14 +24,13 @@ int main(int argc, char *argv[]) {
2424
QString depthmapPath = base + "testcenterRel_copia/photogrammetry/Malt/Z_Num7_DeZoom4_STD-MALT.tif";
2525
QString orientationXmlPath = base + "testcenterRel_copia/photogrammetry/Ori-Relative/Orientation-L05C12.tif.xml";
2626
QString maskPath = base + "testcenterRel_copia/photogrammetry/Malt/Masq_STD-MALT_DeZoom4.tif";
27-
QString plyFile = base +"testcenterRel_copia/photogrammetry/AperiCloud_Relative_mini.ply";
27+
QString plyFile = base +"testcenterRel_copia/photogrammetry/AperiCloud_Relative__mini.ply";
2828
Depthmap depth;
2929

3030
//output
3131
QString outputPath = base + "testcenterRel_copia/photogrammetry/depthmap_projectL05C13.png";
3232
QString output_mask = base + "testcenterRel_copia/photogrammetry/mask_test.tif";
3333
QString output_depth = base + "testcenterRel_copia/photogrammetry/depth_test.tif";
34-
QString output_text = base + "testcenterRel_copia/photogrammetry/point.txt";
3534

3635
OrthoDepthmap ortho;
3736

@@ -42,34 +41,47 @@ int main(int argc, char *argv[]) {
4241
//ortho.computeNormals();
4342
//ortho.saveNormals(qPrintable(base + "testcenterRel_copia/photogrammetry/original.png"));
4443
//ortho.saveObj(qPrintable(base + "testcenterRel_copia/photogrammetry/original.obj"));
45-
46-
ortho.saveDepth(qPrintable(output_depth));
47-
ortho.saveMask(qPrintable(output_mask));
48-
ortho.loadText(qPrintable(plyFile), qPrintable(output_text));
44+
try{
45+
ortho.saveDepth(qPrintable(output_depth));
46+
ortho.saveMask(qPrintable(output_mask));
47+
ortho.loadPointCloud(qPrintable(plyFile));
48+
} catch(QString e){
49+
cout << qPrintable(e) << endl;
50+
exit(-1);
51+
}
52+
ortho.verifyPointCloud();
53+
ortho.fitLinearRegressionFromPairs();
4954

5055
Camera camera;
5156
camera.loadXml(orientationXmlPath);
57+
CameraDepthmap depthCam;
58+
//xml per camera e tiff per la depth map
59+
depthCam.camera.loadXml(orientationXmlPath);
60+
depthCam.loadDepth(qPrintable(depthmapPath));
61+
ortho.integratedCamera(depthCam);
62+
63+
5264
//int pixelX = 165;
5365
//int pixelY = 144;
5466
//float pixelZ = 4.5;
5567
ortho.projectToCameraDepthMap(camera, outputPath);
5668
Eigen::Matrix3f rotationMatrix;
5769
Eigen::Vector3f center;
5870

59-
// depth.loadMask(qPrintable(maskPath));
60-
// depth.saveDepth(qPrintable(depthmapPath));
61-
// depth.saveMask(qPrintable(maskPath));
71+
// depth.loadMask(qPrintable(maskPath));
72+
// depth.saveDepth(qPrintable(depthmapPath));
73+
// depth.saveMask(qPrintable(maskPath));
6274
//QString maskObjPath = base + "testcenterRel_copia/photogrammetry/mask.obj";
63-
// ortho.saveObj(qPrintable(base + "testcenterRel_copia/photogrammetry/depthmap_projectL05C13.obj"));
75+
ortho.saveObj(qPrintable(base + "testcenterRel_copia/photogrammetry/depthmap_projectL05C13.obj"));
6476

6577

6678
//depth.depthIntegrateNormals();
67-
// ortho.saveObj(qPrintable(base + "testcenterRel_copia/photogrammetry/integrated.obj"));
79+
// ortho.saveObj(qPrintable(base + "testcenterRel_copia/photogrammetry/integrated.obj"));
6880

6981

7082

7183

72-
// modifica maschere e depth map per migliorare la depth
84+
// modifica maschere e depth map per migliorare la depth
7385

7486
/*1. test prendi varie masq e modificale in maniera consistente: 1. masq depth 2. masq per ogni camera, cosa modifico?
7587
tawny usa la masq della depth da rti a ortho piano, quelle per camera le usa quando fa l'orthopiano mosaico
@@ -140,7 +152,7 @@ lineare per la serie di coppie per trovare a e b). Pesa i punti.
140152
//cout << "Coordinate immagine: (" << imageCoords[0] << ", " << imageCoords[1] << ")" << endl;
141153

142154

143-
//d = (h + zerolevel) *f scala
155+
//d = (h + zerolevel) *f scala
144156
return 0;
145157
}
146158

0 commit comments

Comments
 (0)