diff options
author | Wind Yuan <feng.yuan@intel.com> | 2017-11-30 18:02:53 +0800 |
---|---|---|
committer | windyuan <feng.yuan@intel.com> | 2017-11-30 19:47:15 +0800 |
commit | 36d06f77d5280d6c9665e911da183f5dd98bb036 (patch) | |
tree | 4ba90a6c6abee326190cdc44a4f18440647a5203 | |
parent | d01967b8a1e23110256c011d9c6208ed42e8d963 (diff) | |
download | libxcam-36d06f77d5280d6c9665e911da183f5dd98bb036.tar.gz |
stitcher: simplify stitcher interface in camera info
* remove round-view slice size setting in camera info
* check test-soft-image.cpp:parse_camera_info
Signed-off-by: Wind Yuan <feng.yuan@intel.com>
-rw-r--r-- | modules/soft/soft_stitcher.cpp | 49 | ||||
-rw-r--r-- | tests/test-soft-image.cpp | 8 | ||||
-rw-r--r-- | xcore/interface/stitcher.cpp | 70 | ||||
-rw-r--r-- | xcore/interface/stitcher.h | 46 |
4 files changed, 115 insertions, 58 deletions
diff --git a/modules/soft/soft_stitcher.cpp b/modules/soft/soft_stitcher.cpp index 85f8cea..cb98293 100644 --- a/modules/soft/soft_stitcher.cpp +++ b/modules/soft/soft_stitcher.cpp @@ -140,7 +140,9 @@ struct FisheyeDewarp { bool set_dewarp_factor (); XCamReturn set_dewarp_geo_table ( SmartPtr<SoftGeoMapper> mapper, - const CameraInfo &cam_info, const BowlDataConfig &bowl); + const CameraInfo &cam_info, + const Stitcher::RoundViewSlice &view_slice, + const BowlDataConfig &bowl); }; struct Copier { @@ -235,21 +237,25 @@ StitcherImpl::init_dewarp_factors (uint32_t idx) } XCamReturn -FisheyeDewarp::set_dewarp_geo_table (SmartPtr<SoftGeoMapper> mapper, const CameraInfo &cam_info, const BowlDataConfig &bowl) +FisheyeDewarp::set_dewarp_geo_table ( + SmartPtr<SoftGeoMapper> mapper, + const CameraInfo &cam_info, + const Stitcher::RoundViewSlice &view_slice, + const BowlDataConfig &bowl) { PolyFisheyeDewarp fd; fd.set_intrinsic_param (cam_info.calibration.intrinsic); fd.set_extrinsic_param (cam_info.calibration.extrinsic); uint32_t table_width, table_height; - table_width = cam_info.slice_view.width / MAP_FACTOR_X; + table_width = view_slice.width / MAP_FACTOR_X; table_width = XCAM_ALIGN_UP (table_width, 4); - table_height = cam_info.slice_view.height / MAP_FACTOR_Y; + table_height = view_slice.height / MAP_FACTOR_Y; table_height = XCAM_ALIGN_UP (table_height, 2); SurViewFisheyeDewarp::MapTable map_table(table_width * table_height); fd.fisheye_dewarp ( map_table, table_width, table_height, - cam_info.slice_view.width, cam_info.slice_view.height, bowl); + view_slice.width, view_slice.height, bowl); XCAM_FAIL_RETURN ( ERROR, mapper->set_lookup_table (map_table.data (), table_width, table_height), @@ -283,14 +289,14 @@ StitcherImpl::init_fisheye (uint32_t idx) XCAM_ASSERT (fisheye.dewarp.ptr ()); fisheye.dewarp->set_callback (dewarp_cb); - CameraInfo cam_info; - _stitcher->get_camera_info (idx, cam_info); + Stitcher::RoundViewSlice view_slice = + _stitcher->get_round_view_slice (idx); VideoBufferInfo buf_info; buf_info.init ( - V4L2_PIX_FMT_NV12, cam_info.slice_view.width, cam_info.slice_view.height, - XCAM_ALIGN_UP (cam_info.slice_view.width, SOFT_STITCHER_ALIGNMENT_X), - XCAM_ALIGN_UP (cam_info.slice_view.height, SOFT_STITCHER_ALIGNMENT_Y)); + V4L2_PIX_FMT_NV12, view_slice.width, view_slice.height, + XCAM_ALIGN_UP (view_slice.width, SOFT_STITCHER_ALIGNMENT_X), + XCAM_ALIGN_UP (view_slice.height, SOFT_STITCHER_ALIGNMENT_Y)); fisheye.buf_pool = new SoftVideoBufAllocator (buf_info); XCAM_ASSERT (fisheye.buf_pool.ptr ()); @@ -404,24 +410,24 @@ StitcherImpl::fisheye_dewarp_to_table () for (uint32_t i = 0; i < camera_num; ++i) { CameraInfo cam_info; _stitcher->get_camera_info (i, cam_info); + Stitcher::RoundViewSlice view_slice = _stitcher->get_round_view_slice (i); BowlDataConfig bowl = _stitcher->get_bowl_config (); - bowl.angle_start = cam_info.slice_view.hori_angle_start; - bowl.angle_end = format_angle ( - cam_info.slice_view.hori_angle_start + cam_info.slice_view.hori_angle_range); + bowl.angle_start = view_slice.hori_angle_start; + bowl.angle_end = format_angle (view_slice.hori_angle_start + view_slice.hori_angle_range); uint32_t out_width, out_height; _stitcher->get_output_size (out_width, out_height); - _fisheye[i].dewarp->set_output_size (cam_info.slice_view.width, cam_info.slice_view.height); + _fisheye[i].dewarp->set_output_size (view_slice.width, view_slice.height); if (bowl.angle_end < bowl.angle_start) bowl.angle_start -= 360.0f; XCAM_LOG_INFO ( "soft-stitcher:%s camera(idx:%d) info (angle start:%.2f, range:%.2f), bowl info (angle start%.2f, end:%.2f)", XCAM_STR (_stitcher->get_name ()), i, - cam_info.slice_view.hori_angle_start, cam_info.slice_view.hori_angle_range, + view_slice.hori_angle_start, view_slice.hori_angle_range, bowl.angle_start, bowl.angle_end); - XCamReturn ret = _fisheye[i].set_dewarp_geo_table (_fisheye[i].dewarp, cam_info, bowl); + XCamReturn ret = _fisheye[i].set_dewarp_geo_table (_fisheye[i].dewarp, cam_info, view_slice, bowl); XCAM_FAIL_RETURN ( ERROR, xcam_ret_is_ok (ret), ret, "stitcher:%s set dewarp geo table failed, idx:%d.", XCAM_STR (_stitcher->get_name ()), i); @@ -478,7 +484,7 @@ StitcherImpl::feature_match ( const SmartPtr<VideoBuffer> &right_buf, const uint32_t idx) { - const ImageOverlapInfo overlap_info = _stitcher->get_overlap (idx); + const Stitcher::ImageOverlapInfo overlap_info = _stitcher->get_overlap (idx); Rect left_ovlap = overlap_info.left; Rect right_ovlap = overlap_info.right; const VideoBufferInfo left_buf_info = left_buf->get_video_info (); @@ -522,7 +528,7 @@ StitcherImpl::start_single_blender ( const SmartPtr<BlenderParam> ¶m) { SmartPtr<SoftBlender> blender = _overlaps[idx].blender; - const ImageOverlapInfo &overlap_info = _stitcher->get_overlap (idx); + const Stitcher::ImageOverlapInfo &overlap_info = _stitcher->get_overlap (idx); uint32_t out_width, out_height; _stitcher->get_output_size (out_width, out_height); @@ -846,7 +852,12 @@ SoftStitcher::configure_resource (const SmartPtr<Parameters> ¶m) XCAM_UNUSED (param); XCAM_ASSERT (_impl.ptr ()); - XCamReturn ret = estimate_coarse_crops (); + XCamReturn ret = estimate_round_slices (); + XCAM_FAIL_RETURN ( + ERROR, xcam_ret_is_ok (ret), ret, + "soft-stitcher:%s estimate round view slices failed", XCAM_STR (get_name ())); + + ret = estimate_coarse_crops (); XCAM_FAIL_RETURN ( ERROR, xcam_ret_is_ok (ret), ret, "soft-stitcher:%s estimate coarse crops failed", XCAM_STR (get_name ())); diff --git a/tests/test-soft-image.cpp b/tests/test-soft-image.cpp index 444bcfe..1187f79 100644 --- a/tests/test-soft-image.cpp +++ b/tests/test-soft-image.cpp @@ -85,12 +85,8 @@ parse_camera_info (const char *path, uint32_t idx, uint32_t out_w, uint32_t out_ "parse extrinsic params (%s)failed.", extrinsic_path); info.calibration.extrinsic.trans_x += TEST_CAMERA_POSITION_OFFSET_X; - info.slice_view.width = viewpoints_range[idx] / 360.0f * out_w; - info.slice_view.width = XCAM_ALIGN_UP (info.slice_view.width, 32); - info.slice_view.height = out_h; - info.slice_view.hori_angle_range = info.slice_view.width * 360.0f / (float)out_w; - info.slice_view.hori_angle_start = (idx * 360.0f / 4.0f) - info.slice_view.hori_angle_range / 2.0f; - info.slice_view.hori_angle_start = format_angle (info.slice_view.hori_angle_start); + info.angle_range = viewpoints_range[idx]; + info.round_angle_start = (idx * 360.0f / 4.0f) - info.angle_range / 2.0f; return 0; } diff --git a/xcore/interface/stitcher.cpp b/xcore/interface/stitcher.cpp index f98b5d9..c6e3a6a 100644 --- a/xcore/interface/stitcher.cpp +++ b/xcore/interface/stitcher.cpp @@ -25,6 +25,8 @@ // angle to position, output range [-180, 180] #define OUT_WINDOWS_START -180.0f +#define constraint_margin (2 * _alignment_x) + namespace XCam { static inline bool @@ -80,6 +82,7 @@ Stitcher::Stitcher (uint32_t align_x, uint32_t align_y) , _output_height (0) , _out_start_angle (OUT_WINDOWS_START) , _camera_num (0) + , _is_round_view_set (false) , _is_overlap_set (false) , _is_center_marked (false) { @@ -180,11 +183,51 @@ Stitcher::get_camera_info (uint32_t index, CameraInfo &info) const } XCamReturn +Stitcher::estimate_round_slices () +{ + if (_is_round_view_set) + return XCAM_RETURN_NO_ERROR; + + XCAM_FAIL_RETURN ( + ERROR, _camera_num && _camera_num < XCAM_STITCH_MAX_CAMERAS, XCAM_RETURN_ERROR_PARAM, + "stitcher: camera num was not set, or camera num(%d) exceed max camera value(%d)", + _camera_num, XCAM_STITCH_MAX_CAMERAS); + + for (uint32_t i = 0; i < _camera_num; ++i) { + CameraInfo &cam_info = _camera_info[i]; + RoundViewSlice &view_slice = _round_view_slices[i]; + + view_slice.width = cam_info.angle_range / 360.0f * (float)_output_width; + view_slice.width = XCAM_ALIGN_UP (view_slice.width, _alignment_x); + view_slice.height = _output_height; + view_slice.hori_angle_range = view_slice.width * 360.0f / (float)_output_width; + + uint32_t aligned_start = format_angle (cam_info.round_angle_start) / 360.0f * (float)_output_width; + aligned_start = XCAM_ALIGN_AROUND (aligned_start, _alignment_x); + if (_output_width <= constraint_margin + aligned_start || aligned_start <= constraint_margin) + aligned_start = 0; + view_slice.hori_angle_start = format_angle((float)aligned_start / (float)_output_width * 360.0f); + if (XCAM_DOUBLE_EQUAL_AROUND (view_slice.hori_angle_start, 0.0001f)) + view_slice.hori_angle_start = 0.0f; + + cam_info.round_angle_start = view_slice.hori_angle_start; + cam_info.angle_range = view_slice.hori_angle_range; + } + + _is_round_view_set = true; + return XCAM_RETURN_NO_ERROR; +} + +XCamReturn Stitcher::estimate_coarse_crops () { if (_is_crop_set) return XCAM_RETURN_NO_ERROR; + XCAM_FAIL_RETURN ( + ERROR, _camera_num > 0 && _is_round_view_set, XCAM_RETURN_ERROR_ORDER, + "stitcher mark_centers failed, need set camera info and round_slices first"); + for (uint32_t i = 0; i < _camera_num; ++i) { _crop_info[i].left = 0; _crop_info[i].right = 0; @@ -199,23 +242,21 @@ Stitcher::estimate_coarse_crops () XCamReturn Stitcher::mark_centers () { - const uint32_t constraint_margin = 2 * _alignment_x; - if (_is_center_marked) return XCAM_RETURN_NO_ERROR; XCAM_FAIL_RETURN ( - ERROR, _camera_num > 0, XCAM_RETURN_ERROR_ORDER, - "stitcher mark_centers failed, need set camera info first"); + ERROR, _camera_num > 0 && _is_round_view_set, XCAM_RETURN_ERROR_ORDER, + "stitcher mark_centers failed, need set camera info and round_view slices first"); for (uint32_t i = 0; i < _camera_num; ++i) { - const RoundViewSlice &slice = _camera_info[i].slice_view; + const RoundViewSlice &slice = _round_view_slices[i]; //calcuate final output postion float center_angle = i * 360.0f / _camera_num; uint32_t out_pos = format_angle (center_angle - _out_start_angle) / 360.0f * _output_width; XCAM_ASSERT (out_pos < _output_width); - if (_output_width - out_pos < constraint_margin || out_pos < constraint_margin) + if (_output_width <= constraint_margin + out_pos || out_pos <= constraint_margin) out_pos = 0; // get slice center angle @@ -249,13 +290,13 @@ Stitcher::estimate_overlap () return XCAM_RETURN_NO_ERROR; XCAM_FAIL_RETURN ( - ERROR, _is_crop_set && _is_center_marked, XCAM_RETURN_ERROR_ORDER, - "stitcher estimate_coarse_seam failed, need set crop info first"); + ERROR, _is_round_view_set && _is_crop_set && _is_center_marked, XCAM_RETURN_ERROR_ORDER, + "stitcher estimate_coarse_seam failed, need set round_view slices, crop info and mark centers first"); for (uint32_t idx = 0; idx < _camera_num; ++idx) { uint32_t next_idx = (idx + 1) % _camera_num; - const RoundViewSlice &left = _camera_info[idx].slice_view; - const RoundViewSlice &right = _camera_info[next_idx].slice_view; + const RoundViewSlice &left = _round_view_slices[idx]; + const RoundViewSlice &right = _round_view_slices[next_idx]; const CenterMark &left_center = _center_marks[idx]; const CenterMark &right_center = _center_marks[next_idx]; const ImageCropInfo &left_img_crop = _crop_info[idx]; @@ -391,8 +432,9 @@ XCamReturn Stitcher::update_copy_areas () { XCAM_FAIL_RETURN ( - ERROR, _camera_num > 1 && _is_crop_set && _is_overlap_set, XCAM_RETURN_ERROR_ORDER, - "stitcher update_copy_areas failed, check orders, need camera_info, crop_info and overlap_info set first."); + ERROR, _camera_num > 1 && _is_round_view_set && _is_crop_set && _is_overlap_set, XCAM_RETURN_ERROR_ORDER, + "stitcher update_copy_areas failed, check orders, need" + "camera_info, round_view slices, crop_info and overlap_info set first."); CopyAreaArray tmp_areas; uint32_t i = 0; @@ -411,7 +453,7 @@ Stitcher::update_copy_areas () left.in_area.width = overlap.left.pos_x - left.in_area.pos_x; XCAM_ASSERT (left.in_area.width > 0); left.in_area.pos_y = _crop_info[i].top; - left.in_area.height = _camera_info[i].slice_view.height - _crop_info[i].top - _crop_info[i].bottom; + left.in_area.height = _round_view_slices[i].height - _crop_info[i].top - _crop_info[i].bottom; XCAM_ASSERT (left.in_area.height > 0); left.out_area.pos_x = mark_left.out_center_x; @@ -432,7 +474,7 @@ Stitcher::update_copy_areas () right.in_area.width = (int32_t)mark_right.slice_center_x - right.in_area.pos_x; XCAM_ASSERT (right.in_area.width > 0); right.in_area.pos_y = _crop_info[next_i].top; - right.in_area.height = _camera_info[next_i].slice_view.height - _crop_info[next_i].top - _crop_info[next_i].bottom; + right.in_area.height = _round_view_slices[next_i].height - _crop_info[next_i].top - _crop_info[next_i].bottom; XCAM_ASSERT (right.in_area.height > 0); uint32_t out_right_center_x = mark_right.out_center_x; diff --git a/xcore/interface/stitcher.h b/xcore/interface/stitcher.h index efcf452..39b875e 100644 --- a/xcore/interface/stitcher.h +++ b/xcore/interface/stitcher.h @@ -64,32 +64,27 @@ struct CalibrationInfo { IntrinsicParameter intrinsic; }; -struct RoundViewSlice { - float hori_angle_start; - float hori_angle_range; - uint32_t width; - uint32_t height; - - RoundViewSlice () - : hori_angle_start (0.0f), hori_angle_range (0.0f) - , width (0), height (0) - {} -}; - struct CameraInfo { CalibrationInfo calibration; - RoundViewSlice slice_view; -}; - -struct ImageOverlapInfo { - Rect left; - Rect right; - Rect out_area; + float round_angle_start; + float angle_range;; }; class Stitcher { public: + struct RoundViewSlice { + float hori_angle_start; + float hori_angle_range; + uint32_t width; + uint32_t height; + + RoundViewSlice () + : hori_angle_start (0.0f), hori_angle_range (0.0f) + , width (0), height (0) + {} + }; + struct CenterMark { uint32_t slice_center_x; uint32_t out_center_x; @@ -109,6 +104,12 @@ public: {} }; + struct ImageOverlapInfo { + Rect left; + Rect right; + Rect out_area; + }; + struct CopyArea { uint32_t in_idx; Rect in_area; @@ -160,6 +161,7 @@ public: virtual XCamReturn stitch_buffers (const VideoBufferList &in_bufs, SmartPtr<VideoBuffer> &out_buf) = 0; protected: + XCamReturn estimate_round_slices (); virtual XCamReturn estimate_coarse_crops (); XCamReturn mark_centers (); XCamReturn estimate_overlap (); @@ -168,6 +170,9 @@ protected: const CenterMark &get_center (uint32_t idx) const { return _center_marks[idx]; } + const RoundViewSlice &get_round_view_slice (uint32_t idx) const { + return _round_view_slices[idx]; + } const ImageOverlapInfo &get_overlap (uint32_t idx) const { return _overlap_info[idx]; } @@ -193,6 +198,9 @@ private: float _out_start_angle; uint32_t _camera_num; CameraInfo _camera_info[XCAM_STITCH_MAX_CAMERAS]; + RoundViewSlice _round_view_slices[XCAM_STITCH_MAX_CAMERAS]; + bool _is_round_view_set; + ImageOverlapInfo _overlap_info[XCAM_STITCH_MAX_CAMERAS]; BowlDataConfig _bowl_config; bool _is_overlap_set; |