Commit 413abf1f authored by Ayush Mittal's avatar Ayush Mittal Committed by Alexandru Băluț
Browse files

Revisit how set_combo_value is used

The method is applied to the project video framerate, to the audio rate,
and to the audio channels number. In addition, in the Render dialog it's
applied to the muxer and to the encoder(s).

- The audio widgets should always succeed as we don't allow custom
  values.

- The muxer is allowed to fail as it means it's missing from the current
  system, and maybe the user wants to render using a different one.

- Similarly, we pick the first available encoder if the preferred one
  cannot be found.

- The video framerate is allowed to fail as we allow setting a custom
  framerate.

Fixes #2425
parent a506fe1b
Pipeline #158678 failed with stages
in 10 seconds
......@@ -2086,11 +2086,11 @@ class ProjectSettingsDialog:
self.widgets_group = RippleUpdateGroup()
self.widgets_group.add_vertex(self.frame_rate_combo,
signal="changed",
update_func=self._update_combo_func,
update_func=self._update_frame_rate_combo_func,
update_func_args=(self.frame_rate_fraction_widget,))
self.widgets_group.add_vertex(self.frame_rate_fraction_widget,
signal="value-changed",
update_func=self._update_fraction_func,
update_func=self._update_frame_rate_fraction_func,
update_func_args=(self.frame_rate_combo,))
self.widgets_group.add_vertex(self.width_spinbutton, signal="value-changed")
self.widgets_group.add_vertex(self.height_spinbutton, signal="value-changed")
......@@ -2133,15 +2133,13 @@ class ProjectSettingsDialog:
# Bind the widgets in the Video tab to the Video Presets Manager.
self.bind_spinbutton(self.video_presets, "width", self.width_spinbutton)
self.bind_spinbutton(
self.video_presets, "height", self.height_spinbutton)
self.bind_spinbutton(self.video_presets, "height", self.height_spinbutton)
self.bind_fraction_widget(
self.video_presets, "frame-rate", self.frame_rate_fraction_widget)
# Bind the widgets in the Audio tab to the Audio Presets Manager.
self.bind_combo(self.audio_presets, "channels", self.channels_combo)
self.bind_combo(
self.audio_presets, "sample-rate", self.sample_rate_combo)
self.bind_combo(self.audio_presets, "sample-rate", self.sample_rate_combo)
self.widgets_group.add_edge(
self.frame_rate_fraction_widget, self.video_preset_menubutton)
......@@ -2155,9 +2153,10 @@ class ProjectSettingsDialog:
mgr.bind_widget(name, widget.set_widget_value, widget.get_widget_value)
def bind_combo(self, mgr, name, widget):
mgr.bind_widget(name,
lambda x: set_combo_value(widget, x),
lambda: get_combo_value(widget))
def setter(value):
res = set_combo_value(widget, value)
assert res, value
mgr.bind_widget(name, setter, lambda: get_combo_value(widget))
def bind_spinbutton(self, mgr, name, widget):
mgr.bind_widget(name,
......@@ -2170,11 +2169,14 @@ class ProjectSettingsDialog:
def proxy_res_linked(self):
return self.proxy_res_linked_check.props.active
def _update_fraction_func(self, unused, fraction, combo):
fraction.set_widget_value(get_combo_value(combo))
def _update_frame_rate_fraction_func(self, unused, fraction_widget, combo_widget):
"""Updates the fraction_widget to match the combo_widget."""
fraction_widget.set_widget_value(get_combo_value(combo_widget))
def _update_combo_func(self, unused, combo, fraction):
set_combo_value(combo, fraction.get_widget_value())
def _update_frame_rate_combo_func(self, unused, combo_widget, fraction_widget):
"""Updates the combo_widget to match the fraction_widget."""
# This can fail when there is no corresponding value in combo's model.
set_combo_value(combo_widget, fraction_widget.get_widget_value())
def __video_preset_loaded_cb(self, unused_mgr):
self.sar = self.get_sar()
......@@ -2230,8 +2232,11 @@ class ProjectSettingsDialog:
self.video_presets_combo.set_active_id(matching_video_preset)
# Audio
set_combo_value(self.channels_combo, self.project.audiochannels)
set_combo_value(self.sample_rate_combo, self.project.audiorate)
res = set_combo_value(self.channels_combo, self.project.audiochannels)
assert res, self.project.audiochannels
res = set_combo_value(self.sample_rate_combo, self.project.audiorate)
assert res, self.project.audiorate
matching_audio_preset = self.audio_presets.matching_preset(self.project)
if matching_audio_preset:
......
......@@ -637,12 +637,15 @@ class RenderDialog(Loggable):
return model
def _display_settings(self):
"""Displays the settings also in the ProjectSettingsDialog."""
"""Applies the project settings to the UI."""
# Video settings
set_combo_value(self.frame_rate_combo, self.project.videorate)
# Audio settings
set_combo_value(self.channels_combo, self.project.audiochannels)
set_combo_value(self.sample_rate_combo, self.project.audiorate)
res = set_combo_value(self.channels_combo, self.project.audiochannels)
assert res, self.project.audiochannels
res = set_combo_value(self.sample_rate_combo, self.project.audiorate)
assert res, self.project.audiorate
def _update_audio_widgets_sensitivity(self):
active = self.audio_output_checkbutton.get_active()
......@@ -663,14 +666,20 @@ class RenderDialog(Loggable):
self.__update_render_button_sensitivity()
def _display_render_settings(self):
"""Displays the settings available only in the RenderDialog."""
"""Applies the project render settings to the UI."""
# Video settings
# This will trigger an update of the video resolution label.
self.scale_spinbutton.set_value(self.project.render_scale)
# Muxer settings
# This will trigger an update of the codec comboboxes.
set_combo_value(self.muxer_combo,
Encoders().factories_by_name.get(self.project.muxer))
muxer = Encoders().factories_by_name.get(self.project.muxer)
if muxer:
if not set_combo_value(self.muxer_combo, muxer):
# The project's muxer is not available on this system.
# Pick the first one available.
first = self.muxer_combo.props.model.get_iter_first()
set_combo_value(self.muxer_combo, first)
def _check_filename(self):
"""Displays a warning if the file path already exists."""
......@@ -763,8 +772,7 @@ class RenderDialog(Loggable):
reduced_model.append(value)
combo.set_model(reduced_model)
set_combo_value(combo, combo_value)
if get_combo_value(combo) != combo_value:
if not set_combo_value(combo, combo_value):
combo.set_active(len(reduced_model) - 1)
self.warning("%s in %s not supported, setting: %s",
combo_value, caps_template, get_combo_value(combo))
......@@ -819,25 +827,25 @@ class RenderDialog(Loggable):
def _update_encoder_combo(self, encoder_combo, preferred_encoder):
"""Selects the specified encoder for the specified encoder combo."""
if preferred_encoder:
# A preference exists, pick it if it can be found in
# the current model of the combobox.
encoder = Encoders().factories_by_name.get(preferred_encoder)
set_combo_value(encoder_combo, encoder)
if not preferred_encoder or not get_combo_value(encoder_combo):
# No preference exists or it is not available,
# pick the first encoder from the combobox's model.
first = encoder_combo.props.model.get_iter_first()
if not first:
# Model is empty. Should not happen.
self.warning("Model is empty")
if set_combo_value(encoder_combo, encoder):
# The preference was found in the combo's model
# and has been activated.
return
if not encoder_combo.props.model.iter_has_child(first):
# The first item is a supported factory.
encoder_combo.set_active_iter(first)
else:
# The first element is the Unsupported group.
second = encoder_combo.props.model.iter_nth_child(first, 0)
encoder_combo.set_active_iter(second)
# Pick the first encoder from the combobox's model.
first = encoder_combo.props.model.get_iter_first()
if not first:
# Model is empty. Should not happen.
self.warning("Model is empty")
return
if encoder_combo.props.model.iter_has_child(first):
# There are no supported encoders and the first element is
# the Unsupported group. Activate its first child.
first = encoder_combo.props.model.iter_nth_child(first, 0)
encoder_combo.set_active_iter(first)
def _element_settings_dialog(self, factory, media_type):
"""Opens a dialog to edit the properties for the specified factory.
......
......@@ -771,7 +771,7 @@ def set_combo_value(combo, value):
if len(found) != 1:
do_log(INFO, None, "utils",
"Could not set value %s, possible values: %s",
(value, [v[0] for v in combo.props.model]))
(value, [v[1] for v in combo.props.model]))
return False
return True
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment