diff --git a/core/libcamera_app.cpp b/core/libcamera_app.cpp index d3439c24..d3ebf7e0 100644 --- a/core/libcamera_app.cpp +++ b/core/libcamera_app.cpp @@ -631,6 +631,9 @@ void LibcameraApp::StartCamera() controls_.set(controls::Saturation, options_->saturation); if (!controls_.get(controls::Sharpness)) controls_.set(controls::Sharpness, options_->sharpness); + if (!controls_.get(controls::HdrMode) && + (options_->hdr == "auto" || options_->hdr == "single-exp")) + controls_.set(controls::HdrMode, controls::HdrModeSingleExposure); // AF Controls, where supported and not already set if (!controls_.get(controls::AfMode) && camera_->controls().count(&controls::AfMode) > 0) diff --git a/core/options.cpp b/core/options.cpp index e4477010..cfe35a5e 100644 --- a/core/options.cpp +++ b/core/options.cpp @@ -146,10 +146,14 @@ bool Options::Parse(int argc, char *argv[]) shutter.set(shutter_); flicker_period.set(flicker_period_); - // HDR control. Set this before opening or listing any cameras. + if (hdr != "off" && hdr != "single-exp" && hdr != "sensor" && hdr != "auto") + throw std::runtime_error("Invalid HDR option provided: " + hdr); + + // HDR control. Set the sensor control before opening or listing any cameras. // Currently this does not exist in libcamera, so go directly to V4L2 // XXX it's not obvious which v4l2-subdev to use for which camera! { + bool en = (hdr == "auto" || hdr == "sensor"); bool ok = false; for (int i = 0; i < 4 && !ok; i++) { @@ -159,12 +163,14 @@ bool Options::Parse(int argc, char *argv[]) if (fd < 0) continue; - v4l2_control ctrl { V4L2_CID_WIDE_DYNAMIC_RANGE, hdr }; + v4l2_control ctrl { V4L2_CID_WIDE_DYNAMIC_RANGE, en }; ok = !xioctl(fd, VIDIOC_S_CTRL, &ctrl); close(fd); } - if (hdr && !ok) - LOG_ERROR("WARNING: Unable to set HDR mode"); + if (hdr == "sensor" && en && !ok) + LOG_ERROR("WARNING: Unable to set sensor HDR mode"); + else if (hdr == "auto" && en && ok) + hdr = "sensor"; } // We have to pass the tuning file name through an environment variable. @@ -488,8 +494,7 @@ void Options::Print() const << afWindow_height << std::endl; if (!lens_position_.empty()) std::cerr << " lens-position: " << lens_position_ << std::endl; - if (hdr) - std::cerr << " hdr: enabled" << hdr << std::endl; + std::cerr << " hdr: " << hdr << std::endl; std::cerr << " mode: " << mode.ToString() << std::endl; std::cerr << " viewfinder-mode: " << viewfinder_mode.ToString() << std::endl; if (buffer_count > 0) diff --git a/core/options.hpp b/core/options.hpp index e913d6e5..b0daff39 100644 --- a/core/options.hpp +++ b/core/options.hpp @@ -201,8 +201,10 @@ struct Options "Sets AfMetering to AfMeteringWindows an set region used, e.g. 0.25,0.25,0.5,0.5") ("lens-position", value(&lens_position_)->default_value(""), "Set the lens to a particular focus position, expressed as a reciprocal distance (0 moves the lens to infinity), or \"default\" for the hyperfocal distance") - ("hdr", value(&hdr)->default_value(false)->implicit_value(true), - "Enable (1) or disable (0) High Dynamic Range, where supported") + ("hdr", value(&hdr)->default_value("off")->implicit_value("auto"), + "Enable High Dynamic Range, where supported. Available values are \"off\", \"auto\", " + "\"sensor\" for sensor HDR (e.g. for Camera Module 3), " + "\"single-exp\" for PiSP based single exposure multiframe HDR") ("metadata", value(&metadata), "Save captured image metadata to a file or \"-\" for stdout") ("metadata-format", value(&metadata_format)->default_value("json"), @@ -281,7 +283,7 @@ struct Options bool af_on_capture; std::string metadata; std::string metadata_format; - bool hdr; + std::string hdr; TimeVal flicker_period; bool no_raw;