Skip to content

Commit 37856c6

Browse files
authored
Export poses (#22)
* update dep * clean up * sort poses
1 parent cec1c51 commit 37856c6

File tree

8 files changed

+72
-49
lines changed

8 files changed

+72
-49
lines changed

Cargo.toml

Lines changed: 9 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
[package]
22
name = "camera-intrinsic-calibration"
3-
version = "0.7.2"
4-
edition = "2021"
3+
version = "0.8.0"
4+
edition = "2024"
55
authors = ["Powei Lin <poweilin1994@gmail.com>"]
66
readme = "README.md"
77
license = "GPL-3.0-or-later"
@@ -21,27 +21,27 @@ exclude = [
2121
]
2222

2323
[dependencies]
24-
aprilgrid = "0.6.0"
24+
aprilgrid = "0.6.1"
2525
camera-intrinsic-model = "0.5.0"
2626
clap = { version = "4.5", features = ["derive"] }
2727
colorous = "1.0.16"
2828
env_logger = "0.11.8"
29-
faer = "0.21.9"
30-
glam = "0.30"
29+
faer = "0.22.6"
30+
glam = "0.30.3"
3131
glob = "0.3.2"
3232
image = "0.25.6"
3333
indicatif = { version = "0.17.11", features = ["rayon"] }
3434
log = "0.4.27"
3535
nalgebra = "0.33.2"
36-
rand = "0.9.0"
36+
rand = "0.9.1"
3737
rand_chacha = "0.9.0"
3838
rayon = "1.10.0"
39-
rerun = "0.22.1"
39+
rerun = "0.23.2"
4040
serde = { version = "1.0.219", features = ["derive"] }
4141
serde_json = "1.0.140"
4242
sqpnp_simple = "0.1.6"
43-
time = "0.3.41"
44-
tiny-solver = "0.17.0"
43+
time = { version = "0.3.41", features = ["local-offset"] }
44+
tiny-solver = "0.17.1"
4545

4646
[[bin]]
4747
name = "ccrs"

README.md

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -33,9 +33,9 @@ ccrs dataset-calib-cam1_1024_16 --model eucm
3333
### Visualize details after calibration
3434
```sh
3535
# use cargo to install rerun
36-
cargo install rerun-cli --version 0.22.1
36+
cargo install rerun-cli --version 0.23.2
3737
# or use pip to install rerun
38-
pip install rerun-sdk==0.22.1
38+
pip install rerun-sdk==0.23.2
3939
# visualize result
4040
rerun results/20YYMMDD_HH_MM_SS/logging.rrd
4141
```

src/bin/camera_calibration.rs

Lines changed: 17 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1,18 +1,17 @@
1-
use aprilgrid::detector::TagDetector;
21
use aprilgrid::TagFamily;
2+
use aprilgrid::detector::TagDetector;
33
use camera_intrinsic_calibration::board::Board;
4-
use camera_intrinsic_calibration::board::{
5-
board_config_from_json, board_config_to_json, BoardConfig,
6-
};
4+
use camera_intrinsic_calibration::board::BoardConfig;
75
use camera_intrinsic_calibration::data_loader::{load_euroc, load_others};
86
use camera_intrinsic_calibration::detected_points::FrameFeature;
9-
use camera_intrinsic_calibration::io::{extrinsics_to_json, write_report};
7+
use camera_intrinsic_calibration::io::{object_from_json, object_to_json, write_report};
108
use camera_intrinsic_calibration::types::{CalibParams, Extrinsics, RvecTvec, ToRvecTvec};
119
use camera_intrinsic_calibration::util::*;
1210
use camera_intrinsic_calibration::visualization::*;
1311
use camera_intrinsic_model::*;
1412
use clap::{Parser, ValueEnum};
1513
use log::trace;
14+
use std::collections::BTreeMap;
1615
use std::collections::HashMap;
1716
use std::time::Instant;
1817
use time::OffsetDateTime;
@@ -74,10 +73,10 @@ fn main() {
7473
let cli = CCRSCli::parse();
7574
let detector = TagDetector::new(&cli.tag_family, None);
7675
let board = if let Some(board_config_path) = cli.board_config {
77-
Board::from_config(&board_config_from_json(&board_config_path))
76+
Board::from_config(&object_from_json(&board_config_path))
7877
} else {
7978
let config = BoardConfig::default();
80-
board_config_to_json("default_board_config.json", &config);
79+
object_to_json("default_board_config.json", &config);
8180
Board::from_config(&config)
8281
};
8382
let dataset_root = &cli.path;
@@ -199,6 +198,12 @@ fn main() {
199198
)
200199
})
201200
.collect();
201+
object_to_json(
202+
&format!("{}/cam{}_poses.json", output_folder, cam_idx),
203+
&new_rtvec_map
204+
.iter()
205+
.collect::<BTreeMap<&usize, &RvecTvec>>(),
206+
);
202207
let cam_transform =
203208
na_isometry3_to_rerun_transform3d(&t_i_0[cam_idx].to_na_isometry3().inverse())
204209
.with_axis_length(0.1);
@@ -221,7 +226,7 @@ fn main() {
221226
}
222227
write_report(&format!("{}/report.txt", output_folder), true, &rep_rms);
223228

224-
extrinsics_to_json(
229+
object_to_json(
225230
&format!("{}/extrinsics.json", output_folder),
226231
&Extrinsics::new(&t_i_0),
227232
);
@@ -244,6 +249,10 @@ fn main() {
244249
serde_json::to_string_pretty(intrinsic).unwrap()
245250
);
246251
model_to_json(&format!("{}/cam{}.json", output_folder, cam_idx), intrinsic);
252+
object_to_json(
253+
&format!("{}/cam{}_poses.json", output_folder, cam_idx),
254+
&rtvec_map.iter().collect::<BTreeMap<&usize, &RvecTvec>>(),
255+
);
247256
}
248257
write_report(&format!("{}/report.txt", output_folder), false, &rep_rms);
249258
}

src/board.rs

Lines changed: 1 addition & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
use glam;
22
use serde::{Deserialize, Serialize};
3-
use std::{collections::HashMap, io::Write};
3+
use std::collections::HashMap;
44

55
#[derive(Debug, Serialize, Deserialize)]
66
pub struct BoardConfig {
@@ -11,18 +11,6 @@ pub struct BoardConfig {
1111
first_id: u32,
1212
}
1313

14-
pub fn board_config_to_json(output_path: &str, board_config: &BoardConfig) {
15-
let j = serde_json::to_string_pretty(board_config).unwrap();
16-
let mut file = std::fs::File::create(output_path).unwrap();
17-
file.write_all(j.as_bytes()).unwrap();
18-
}
19-
20-
pub fn board_config_from_json(file_path: &str) -> BoardConfig {
21-
let contents =
22-
std::fs::read_to_string(file_path).expect("Should have been able to read the file");
23-
serde_json::from_str(&contents).unwrap()
24-
}
25-
2614
impl Default for BoardConfig {
2715
fn default() -> Self {
2816
Self {

src/data_loader.rs

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ use glob::glob;
1010
use image::{DynamicImage, ImageReader};
1111
use indicatif::ParallelProgressIterator;
1212
use rayon::prelude::*;
13+
use rerun::TimeCell;
1314

1415
const MIN_CORNERS: usize = 24;
1516

@@ -98,7 +99,10 @@ pub fn load_euroc(
9899
let time_ns = path_to_timestamp(path);
99100
let img = ImageReader::open(path).unwrap().decode().unwrap();
100101
if let Some(recording) = recording_option {
101-
recording.set_time_nanos("stable", time_ns);
102+
recording.set_time(
103+
"stable",
104+
TimeCell::from_timestamp_nanos_since_epoch(time_ns),
105+
);
102106
let topic = format!("cam{}", cam_idx);
103107
log_image(recording, &topic, &img);
104108
};
@@ -152,7 +156,10 @@ pub fn load_others(
152156
let time_ns = *idx as i64 * 100000000;
153157
let img = ImageReader::open(path).unwrap().decode().unwrap();
154158
if let Some(recording) = recording_option {
155-
recording.set_time_nanos("stable", time_ns);
159+
recording.set_time(
160+
"stable",
161+
TimeCell::from_timestamp_nanos_since_epoch(time_ns),
162+
);
156163
let topic = format!("cam{}", cam_idx);
157164
log_image(recording, &topic, &img);
158165
};

src/io.rs

Lines changed: 8 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,17 @@
11
use std::io::Write;
22

3-
use crate::types::Extrinsics;
3+
use serde::{Serialize, de::DeserializeOwned};
44

5-
pub fn extrinsics_to_json(output_path: &str, extrinsic: &Extrinsics) {
6-
let j = serde_json::to_string_pretty(extrinsic).unwrap();
5+
pub fn object_to_json<T: Serialize>(output_path: &str, object: &T) {
6+
let j = serde_json::to_string_pretty(object).unwrap();
77
let mut file = std::fs::File::create(output_path).unwrap();
88
file.write_all(j.as_bytes()).unwrap();
99
}
10+
pub fn object_from_json<T: DeserializeOwned>(file_path: &str) -> T {
11+
let contents =
12+
std::fs::read_to_string(file_path).expect("Should have been able to read the file");
13+
serde_json::from_str(&contents).unwrap()
14+
}
1015

1116
pub fn write_report(output_path: &str, with_extrinsic: bool, rep_rms: &[(f64, f64)]) {
1217
let mut s = String::new();

src/util.rs

Lines changed: 15 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -13,15 +13,15 @@ use log::debug;
1313
use nalgebra as na;
1414
use rand::seq::SliceRandom;
1515
use rerun::RecordingStream;
16-
use tiny_solver::loss_functions::HuberLoss;
1716
use tiny_solver::Optimizer;
17+
use tiny_solver::loss_functions::HuberLoss;
1818

1919
pub fn rtvec_to_na_dvec(
2020
rtvec: ((f64, f64, f64), (f64, f64, f64)),
2121
) -> (na::DVector<f64>, na::DVector<f64>) {
2222
(
23-
na::dvector![rtvec.0 .0, rtvec.0 .1, rtvec.0 .2],
24-
na::dvector![rtvec.1 .0, rtvec.1 .1, rtvec.1 .2],
23+
na::dvector![rtvec.0.0, rtvec.0.1, rtvec.0.2],
24+
na::dvector![rtvec.1.0, rtvec.1.1, rtvec.1.2],
2525
)
2626
}
2727

@@ -708,7 +708,10 @@ pub fn validation(
708708
(p3p.x, p3p.y, p3p.z)
709709
})
710710
.collect();
711-
recording.set_time_nanos("stable", f.time_ns);
711+
recording.set_time(
712+
"stable",
713+
rerun::TimeCell::from_timestamp_nanos_since_epoch(f.time_ns),
714+
);
712715
recording
713716
.log(
714717
format!("/cam{}/board", cam_idx),
@@ -758,7 +761,10 @@ pub fn validation(
758761
((c.r, c.g, c.b, 255), format!("{}", r))
759762
})
760763
.unzip();
761-
recording.set_time_nanos("stable", *time_ns);
764+
recording.set_time(
765+
"stable",
766+
rerun::TimeCell::from_timestamp_nanos_since_epoch(*time_ns),
767+
);
762768
recording
763769
.log(
764770
topic.to_string(),
@@ -843,7 +849,10 @@ pub fn init_and_calibrate_one_camera(
843849
let key_frames = [Some(frame_feature0.clone()), Some(frame_feature1.clone())];
844850
key_frames.iter().enumerate().for_each(|(i, k)| {
845851
let topic = format!("/cam{}/keyframe{}", cam_idx, i);
846-
recording.set_time_nanos("stable", k.clone().unwrap().time_ns);
852+
recording.set_time(
853+
"stable",
854+
rerun::TimeCell::from_timestamp_nanos_since_epoch(k.clone().unwrap().time_ns),
855+
);
847856
recording
848857
.log(topic, &rerun::TextLog::new("keyframe"))
849858
.unwrap();

src/visualization.rs

Lines changed: 11 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,5 @@
1+
use std::io::Cursor;
2+
13
use image::DynamicImage;
24
use rand::prelude::*;
35
use rand_chacha::ChaCha8Rng;
@@ -6,11 +8,11 @@ use rerun::RecordingStream;
68
use crate::detected_points::FrameFeature;
79

810
pub fn log_image(recording: &RecordingStream, topic: &str, img: &DynamicImage) {
9-
let gray_img = img.to_luma8();
10-
let rr_image = rerun::Image::from_l8(gray_img.to_vec(), [gray_img.width(), gray_img.height()]);
11-
recording
12-
.log(format!("{}/image", topic), &rr_image)
13-
.unwrap();
11+
let mut bytes: Vec<u8> = Vec::new();
12+
img.write_to(&mut Cursor::new(&mut bytes), image::ImageFormat::Png)
13+
.expect("not able to write png");
14+
let rr_image = rerun::EncodedImage::from_file_contents(bytes);
15+
recording.log(topic.to_string(), &rr_image).unwrap();
1416
}
1517

1618
pub fn id_to_color(id: usize) -> (u8, u8, u8, u8) {
@@ -55,7 +57,10 @@ pub fn log_feature_frames(
5557
let (colors, labels): (Vec<_>, Vec<_>) = colors_labels.iter().cloned().unzip();
5658
let pts = rerun_shift(&pts);
5759

58-
recording.set_time_nanos("stable", time_ns);
60+
recording.set_time(
61+
"stable",
62+
rerun::TimeCell::from_timestamp_nanos_since_epoch(time_ns),
63+
);
5964
recording
6065
.log(
6166
format!("{}/pts", topic),

0 commit comments

Comments
 (0)