x
This commit is contained in:
8
README.md
Normal file
8
README.md
Normal file
@ -0,0 +1,8 @@
|
||||
# ChArUco experiments
|
||||
|
||||
go to [`opencv_contrib/modules/aruco/misc/pattern_generator`](https://github.com/opencv/opencv_contrib/tree/4.x/modules/aruco/misc/pattern_generator) to generate custom patterns.
|
||||
|
||||
See also [gen.sh](gen.sh) (put it in the same directory as the pattern generator).
|
||||
|
||||
- A0 size, 10x7, square 115mm, marker 90mm
|
||||
- 400mm x 400mm ArUco board (4x4, 0-5 id)
|
||||
64
dlt.md
Normal file
64
dlt.md
Normal file
@ -0,0 +1,64 @@
|
||||
Direct Linear Transform (DLT) is fundamentally connected to triangulation through its ability to solve the intersection of projection rays. Here's how they relate:
|
||||
|
||||
**Mathematical Foundation:**
|
||||
|
||||
1. **Projection Model**
|
||||
- A 3D point $X = [X,Y,Z,1]^T$ projects to 2D point $x = [u,v,1]^T$ through:
|
||||
$\lambda x = PX$
|
||||
where $P$ is the 3×4 projection matrix
|
||||
$\lambda$ is the projective depth
|
||||
|
||||
2. **DLT Formulation**
|
||||
- For each image point, we can write:
|
||||
$\lambda u = \frac{P_{1}^TX}{P_{3}^TX}$
|
||||
$\lambda v = \frac{P_{2}^TX}{P_{3}^TX}$
|
||||
|
||||
- This leads to linear equations:
|
||||
$uP_{3}^TX - P_{1}^TX = 0$
|
||||
$vP_{3}^TX - P_{2}^TX = 0$
|
||||
|
||||
3. **Triangulation System**
|
||||
- For two views with points $x_1=(u_1,v_1)$ and $x_2=(u_2,v_2)$:
|
||||
|
||||
$$\begin{bmatrix}
|
||||
u_1P_{3,1}^T - P_{1,1}^T \\
|
||||
v_1P_{3,1}^T - P_{2,1}^T \\
|
||||
u_2P_{3,2}^T - P_{1,2}^T \\
|
||||
v_2P_{3,2}^T - P_{2,2}^T
|
||||
\end{bmatrix} X = 0$$
|
||||
|
||||
**Why DLT Works for Triangulation:**
|
||||
|
||||
1. **Geometric Interpretation**
|
||||
- DLT finds the 3D point that minimizes algebraic error
|
||||
- Each row in the equation system represents a constraint from one coordinate
|
||||
- The solution is the intersection of projection rays in 3D space
|
||||
|
||||
2. **Solution Method**
|
||||
- The system $AX = 0$ is solved using SVD
|
||||
- The solution is the eigenvector corresponding to smallest singular value
|
||||
- This provides the optimal 3D point in a least-squares sense
|
||||
|
||||
3. **Implementation Connection**
|
||||
In your code:
|
||||
|
||||
```python
|
||||
A = [
|
||||
point1[1]*P1[2,:] - P1[1,:],
|
||||
P1[0,:] - point1[0]*P1[2,:],
|
||||
point2[1]*P2[2,:] - P2[1,:],
|
||||
P2[0,:] - point2[0]*P2[2,:],
|
||||
]
|
||||
```
|
||||
This directly implements the linear system described above.
|
||||
|
||||
**Advantages:**
|
||||
- Linear solution
|
||||
- Simple to implement
|
||||
- Works with multiple views
|
||||
- Computationally efficient
|
||||
|
||||
**Limitations:**
|
||||
- Sensitive to noise
|
||||
- Assumes perfect point correspondences
|
||||
- Minimizes algebraic (not geometric) error
|
||||
47
gen.sh
Normal file
47
gen.sh
Normal file
@ -0,0 +1,47 @@
|
||||
SQUARE_MM=115
|
||||
MARKER_MM=90
|
||||
MARKER_SEP_MM=$(echo "scale=4; $SQUARE_MM - $MARKER_MM" | bc)
|
||||
|
||||
if [ $MARKER_SEP_MM -lt 0 ]; then
|
||||
echo "Marker size must be smaller than square size"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
SQUARE_SIZE=$(echo "scale=4; $SQUARE_MM / 1000" | bc)
|
||||
MARKER_SIZE=$(echo "scale=4; $MARKER_MM / 1000" | bc)
|
||||
MARKER_SEP=$(echo "scale=4; $MARKER_SEP_MM / 1000" | bc)
|
||||
|
||||
PAGE_PADDING_MM=10
|
||||
PAGE_PADDING=$(echo "scale=4; $PAGE_PADDING_MM / 1000" | bc)
|
||||
|
||||
# A0
|
||||
PAGE_WIDTH_MM=1189
|
||||
PAGE_HEIGHT_MM=841
|
||||
|
||||
BOARD_WIDTH_IN_SQUARE=$(echo "scale=0; ($PAGE_WIDTH_MM - $PAGE_PADDING_MM) / $SQUARE_MM" | bc)
|
||||
BOARD_HEIGHT_IN_SQUARE=$(echo "scale=0; ($PAGE_HEIGHT_MM - $PAGE_PADDING_MM) / $SQUARE_MM" | bc)
|
||||
START_MARKER_ID=10
|
||||
|
||||
OUTPUT_FILENAME="charuco_${PAGE_WIDTH_MM}x${PAGE_HEIGHT_MM}_${BOARD_WIDTH_IN_SQUARE}x${BOARD_HEIGHT_IN_SQUARE}_s${SQUARE_MM}_m${MARKER_MM}.pdf"
|
||||
|
||||
# DICT_4X4_1000
|
||||
# DICT_5X5_1000
|
||||
# DICT_6X6_1000
|
||||
# DICT_7X7_1000
|
||||
# DICT_ARUCO_ORIGINAL
|
||||
# DICT_APRILTAG_16h5
|
||||
# DICT_APRILTAG_25h9
|
||||
# DICT_APRILTAG_36h10
|
||||
# DICT_APRILTAG_36h11
|
||||
|
||||
python MarkerPrinter.py --charuco \
|
||||
--file $OUTPUT_FILENAME \
|
||||
--dictionary DICT_4X4_1000 \
|
||||
--page_border_x $PAGE_PADDING \
|
||||
--page_border_y $PAGE_PADDING \
|
||||
--square_length $SQUARE_SIZE \
|
||||
--marker_length $MARKER_SIZE \
|
||||
--marker_separation $MARKER_SEP \
|
||||
--charuco_size_x $BOARD_WIDTH_IN_SQUARE \
|
||||
--charuco_size_y $BOARD_HEIGHT_IN_SQUARE \
|
||||
--first_marker $START_MARKER_ID
|
||||
Reference in New Issue
Block a user