[libcamera-devel] [PATCH 4/5] libcamera: raspberrypi: ALSC: Handle transform in colour tables
Laurent Pinchart
laurent.pinchart at ideasonboard.com
Wed Jul 29 17:29:57 CEST 2020
Hi David,
Thank you for the patch.
On Wed, Jul 29, 2020 at 10:31:53AM +0100, David Plowman wrote:
> This commit updates ALSC (Auto Lens Shading Correction) to handle the
> transform now passed in the SwitchMode method.
>
> The transform is applied by the sensor, so the statistics we get
> already incorporates it, and the adpative algorithm is agnostic to
> it. That leaves only the calibrated tables (assumed measured without
> any user transform) that need to be flipped, and resample_cal_table -
> where we resample the calibrated table anyway - is an easy place to do
> it.
> ---
> src/ipa/raspberrypi/controller/rpi/alsc.cpp | 22 ++++++++++++++-------
> src/ipa/raspberrypi/controller/rpi/alsc.hpp | 3 ++-
> 2 files changed, 17 insertions(+), 8 deletions(-)
>
> diff --git a/src/ipa/raspberrypi/controller/rpi/alsc.cpp b/src/ipa/raspberrypi/controller/rpi/alsc.cpp
> index 5fac9dd..33c1a88 100644
> --- a/src/ipa/raspberrypi/controller/rpi/alsc.cpp
> +++ b/src/ipa/raspberrypi/controller/rpi/alsc.cpp
> @@ -151,8 +151,9 @@ static void get_cal_table(double ct,
> std::vector<AlscCalibration> const &calibrations,
> double cal_table[XY]);
> static void resample_cal_table(double const cal_table_in[XY],
> - CameraMode const &camera_mode,
> - double cal_table_out[XY]);
> + CameraMode const &camera_mode,
> + Transform transform,
> + double cal_table_out[XY]);
:set tabstop=8
but you may not be using vim :-)
> static void compensate_lambdas_for_cal(double const cal_table[XY],
> double const old_lambdas[XY],
> double new_lambdas[XY]);
> @@ -187,6 +188,7 @@ void Alsc::SwitchMode(CameraMode const &camera_mode, Transform transform, Metada
> // change, any effects should be transient, and if they're not transient
> // enough, we'll revisit the question then.
> camera_mode_ = camera_mode;
> + transform_ = transform;
> if (first_time_) {
> // On the first time, arrange for something sensible in the
> // initial tables. Construct the tables for some default colour
> @@ -194,9 +196,9 @@ void Alsc::SwitchMode(CameraMode const &camera_mode, Transform transform, Metada
> // adaptive algorithm.
> double cal_table_r[XY], cal_table_b[XY], cal_table_tmp[XY];
> get_cal_table(4000, config_.calibrations_Cr, cal_table_tmp);
> - resample_cal_table(cal_table_tmp, camera_mode_, cal_table_r);
> + resample_cal_table(cal_table_tmp, camera_mode_, transform_, cal_table_r);
> get_cal_table(4000, config_.calibrations_Cb, cal_table_tmp);
> - resample_cal_table(cal_table_tmp, camera_mode_, cal_table_b);
> + resample_cal_table(cal_table_tmp, camera_mode_, transform_, cal_table_b);
> compensate_lambdas_for_cal(cal_table_r, lambda_r_,
> async_lambda_r_);
> compensate_lambdas_for_cal(cal_table_b, lambda_b_,
> @@ -379,7 +381,9 @@ void get_cal_table(double ct, std::vector<AlscCalibration> const &calibrations,
> }
>
> void resample_cal_table(double const cal_table_in[XY],
> - CameraMode const &camera_mode, double cal_table_out[XY])
> + CameraMode const &camera_mode,
> + Transform transform,
> + double cal_table_out[XY])
> {
> // Precalculate and cache the x sampling locations and phases to save
> // recomputing them on every row.
> @@ -395,6 +399,8 @@ void resample_cal_table(double const cal_table_in[XY],
> xf[i] = x - x_lo[i];
> x_hi[i] = std::min(x_lo[i] + 1, X - 1);
> x_lo[i] = std::max(x_lo[i], 0);
> + if (transform.contains(Transform::hflip()))
> + x_lo[i] = X - 1 - x_lo[i], x_hi[i] = X - 1 - x_hi[i];
if (transform.contains(Transform::hflip())) {
x_lo[i] = X - 1 - x_lo[i];
x_hi[i] = X - 1 - x_hi[i];
}
No need to hide the code :-)
> }
> // Now march over the output table generating the new values.
> double scale_y = camera_mode.sensor_height /
> @@ -407,6 +413,8 @@ void resample_cal_table(double const cal_table_in[XY],
> double yf = y - y_lo;
> int y_hi = std::min(y_lo + 1, Y - 1);
> y_lo = std::max(y_lo, 0);
> + if (transform.contains(Transform::vflip()))
> + y_lo = Y - 1 - y_lo, y_hi = Y - 1 - y_hi;
Same here.
> double const *row_above = cal_table_in + X * y_lo;
> double const *row_below = cal_table_in + X * y_hi;
> for (int i = 0; i < X; i++) {
> @@ -671,9 +679,9 @@ void Alsc::doAlsc()
> // Fetch the new calibrations (if any) for this CT. Resample them in
> // case the camera mode is not full-frame.
> get_cal_table(ct_, config_.calibrations_Cr, cal_table_tmp);
> - resample_cal_table(cal_table_tmp, async_camera_mode_, cal_table_r);
> + resample_cal_table(cal_table_tmp, async_camera_mode_, transform_, cal_table_r);
> get_cal_table(ct_, config_.calibrations_Cb, cal_table_tmp);
> - resample_cal_table(cal_table_tmp, async_camera_mode_, cal_table_b);
> + resample_cal_table(cal_table_tmp, async_camera_mode_, transform_, cal_table_b);
> // You could print out the cal tables for this image here, if you're
> // tuning the algorithm...
> (void)print_cal_table;
> diff --git a/src/ipa/raspberrypi/controller/rpi/alsc.hpp b/src/ipa/raspberrypi/controller/rpi/alsc.hpp
> index 9b54578..9001e8a 100644
> --- a/src/ipa/raspberrypi/controller/rpi/alsc.hpp
> +++ b/src/ipa/raspberrypi/controller/rpi/alsc.hpp
> @@ -60,7 +60,8 @@ private:
> // configuration is read-only, and available to both threads
> AlscConfig config_;
> bool first_time_;
> - std::atomic<CameraMode> camera_mode_;
> + CameraMode camera_mode_;
This seems unrelated. If you don't want to split it to a separate patch,
could you please mention it in the commit message with a rationale ?
> + libcamera::Transform transform_;
> std::thread async_thread_;
> void asyncFunc(); // asynchronous thread function
> std::mutex mutex_;
--
Regards,
Laurent Pinchart
More information about the libcamera-devel
mailing list