Rolling Shutter Correction
Implement a rolling shutter correction algorithm to rectify distorted video frames using gyroscope data. This task involves compensating for the skew caused by camera rotation during the rolling shutter capture process, where each row is captured at a slightly different time.
The rolling shutter effect is a consequence of the way images are captured in most cameras, where the sensor reads out the pixel values row by row, rather than all at once. When the camera rotates during this process, it results in a skewed image, which can be modeled using affine transformations. The gyroscope data provides the per-row rotation, which can be used to apply an inverse transformation to correct the distortion.
To achieve this, the following steps are involved:
- Understand the rotation matrix and how it relates to the gyroscope data.
- Apply the inverse rotation to each row of the image.
- Resample: each output pixel copies a pixel from the same row of the input, at the (generally non-integer) source column rounded down.
Exact mapping
For a frame of height and width , let , and , the inverse of row 's rotation . Output pixel takes its value from input row , column , where
(the first row of the rotation above, applied about the image centre). If or , the output pixel is . For RGB frames all three channels are copied together. Return an 8-bit unsigned integer array with the same shape as the input.
This technique is widely used in video stabilization applications.
Example
Frame and rotation per row
Corrected frame
- Inputs: a grayscale frame with rows , , , , and one angle per row, radians. The centre is .
- Row 1 has angle , so and it is copied unchanged: .
- Row 2 lies on the centre line (), so only the cosine acts: gives . The last pixel reads column 2: .
- Row 0 (, ): gives . The first falls off the left edge, so the row becomes .
- Row 3 (, ): gives , so .
- Output: the corrected frame, a array of 8-bit integers. Notice that rows only shift and stretch sideways, and the shift grows with both the angle and the row's distance from the centre.
Constraints
- Input parameters: image (2D numpy array, grayscale or RGB), rotation_per_row (1D numpy array of angles in radians)
- Valid ranges: Pixel values in [0, 255], rotation angles in [-π, π]
- Output format: Return the corrected frame as a 2D numpy array (same shape and type as input image)
- Special conditions: Assume the input image has a height of at least 2 rows, and the rotation_per_row array has the same length as the number of rows in the image