Skip to content

Commit

Permalink
Handle PR#13060 comments
Browse files Browse the repository at this point in the history
  • Loading branch information
OhadMeir committed Jun 25, 2024
1 parent 68a6fe3 commit aa8a8fd
Showing 1 changed file with 19 additions and 11 deletions.
30 changes: 19 additions & 11 deletions src/ds/d400/d400-private.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -293,18 +293,26 @@ namespace librealsense
//D405 needs special calculation because the ISP crops the full sensor image using non linear transformation.
rs2_intrinsics get_d405_color_stream_intrinsic(const std::vector<uint8_t>& raw_data, uint32_t width, uint32_t height)
{
// Convert normalized focal lenght and principal point to pixel units (K matrix format)
auto k_to_pixels = []( float3x3 & k, ds_rect_resolutions res )
// Convert normalized focal length and principal point to pixel units (K matrix format)
auto normalized_k_to_pixels = [&]( float3x3 & k, ds_rect_resolutions res )
{
if( res == max_ds_rect_resolutions )
throw invalid_value_exception( rsutils::string::from() <<
"Unsupported resolution used (" << width << ", " << height << ")" );

k( 0, 0 ) = k( 0, 0 ) * resolutions_list[res].x / 2.f; // fx
k( 1, 1 ) = k( 1, 1 ) * resolutions_list[res].y / 2.f; // fy
k( 2, 0 ) = ( k( 2, 0 ) + 1 ) * resolutions_list[res].x / 2.f; // ppx
k( 2, 1 ) = ( k( 2, 1 ) + 1 ) * resolutions_list[res].y / 2.f; // ppy
};

// Scale focal lenght and principal point in pixel units from one resolution to another (K matrix format)
auto scale_pixel_k = []( float3x3 & k, ds_rect_resolutions in_res, ds_rect_resolutions out_res )
// Scale focal length and principal point in pixel units from one resolution to another (K matrix format)
auto scale_pixel_k = [&]( float3x3 & k, ds_rect_resolutions in_res, ds_rect_resolutions out_res )
{
if( in_res == max_ds_rect_resolutions || out_res == max_ds_rect_resolutions )
throw invalid_value_exception( rsutils::string::from() <<
"Unsupported resolution used (" << width << ", " << height << ")" );

float scale_x = resolutions_list[out_res].x / static_cast< float >( resolutions_list[in_res].x );
float scale_y = resolutions_list[out_res].y / static_cast< float >( resolutions_list[in_res].y );
float scale = max( scale_x, scale_y );
Expand All @@ -318,30 +326,30 @@ namespace librealsense
};

auto table = check_calib< ds::d400_rgb_calibration_table >( raw_data );
auto raw_res = width_height_to_ds_rect_resolutions( 1280, 800 );
auto output_res = width_height_to_ds_rect_resolutions( width, height );
auto calibration_res = width_height_to_ds_rect_resolutions( table->calib_width, table->calib_height );

float3x3 k = table->intrinsic;
if( output_res == res_1280_720 )
k_to_pixels( k, output_res );
else if( output_res == res_640_480 )
normalized_k_to_pixels( k, output_res );
else if( output_res == res_640_480 ) // 640x480 is 4:3 not 16:9 like other available resolutions. The ISP handling is different.
{
auto raw_res = width_height_to_ds_rect_resolutions( 1280, 800 );
// Extrapolate K to raw resolution
float scale_y = resolutions_list[calibration_res].y / static_cast< float >( resolutions_list[raw_res].y );
k( 1, 1 ) = k( 1, 1 ) * scale_y; // fy
k( 2, 1 ) = k( 2, 1 ) * scale_y; // ppy
k_to_pixels( k, raw_res );
// Handle ISP scaling
normalized_k_to_pixels( k, raw_res );
// Handle ISP scaling to 770x480
auto scale_res = width_height_to_ds_rect_resolutions( 770, 480 );
scale_pixel_k( k, raw_res, scale_res );
// Handle ISP crop
// Handle ISP cropping to 640x480
k( 2, 0 ) = k( 2, 0 ) - ( resolutions_list[scale_res].x - resolutions_list[output_res].x ) / 2; // ppx
k( 2, 1 ) = k( 2, 1 ) - ( resolutions_list[scale_res].y - resolutions_list[output_res].y ) / 2; // ppy
}
else
{
k_to_pixels( k, calibration_res );
normalized_k_to_pixels( k, calibration_res );
scale_pixel_k( k, calibration_res, output_res );
}

Expand Down

0 comments on commit aa8a8fd

Please sign in to comment.