diff --git a/jdaviz/app.py b/jdaviz/app.py index 17c0981c2d..895a0e90b6 100644 --- a/jdaviz/app.py +++ b/jdaviz/app.py @@ -1345,8 +1345,7 @@ def _get_display_unit(self, axis): raise ValueError(f"could not find units for axis='{axis}'") uc = self._jdaviz_helper.plugins.get('Unit Conversion')._obj if axis == 'spectral_y': - # translate options from uc.spectral_y_type to the prefix used in uc.??_unit_selected - axis = {'Surface Brightness': 'sb', 'Flux': 'flux'}[uc.spectral_y_type_selected] + return uc.spectral_y_unit try: return getattr(uc, f'{axis}_unit_selected') except AttributeError: diff --git a/jdaviz/configs/cubeviz/plugins/spectral_extraction/tests/test_spectral_extraction.py b/jdaviz/configs/cubeviz/plugins/spectral_extraction/tests/test_spectral_extraction.py index 084bbca5bf..dc1a6eb4f3 100644 --- a/jdaviz/configs/cubeviz/plugins/spectral_extraction/tests/test_spectral_extraction.py +++ b/jdaviz/configs/cubeviz/plugins/spectral_extraction/tests/test_spectral_extraction.py @@ -584,6 +584,7 @@ def test_spectral_extraction_unit_conv_one_spec( uc = cubeviz_helper.plugins["Unit Conversion"] assert uc.flux_unit == "Jy" uc.flux_unit.selected = "MJy" + assert spectrum_viewer.state.y_display_unit == "MJy" spec_extr_plugin = cubeviz_helper.plugins['Spectral Extraction'] # Overwrite the one and only default extraction. collapsed = spec_extr_plugin.extract() diff --git a/jdaviz/configs/default/plugins/viewers.py b/jdaviz/configs/default/plugins/viewers.py index 4751ba83e4..efd12dec9e 100644 --- a/jdaviz/configs/default/plugins/viewers.py +++ b/jdaviz/configs/default/plugins/viewers.py @@ -773,7 +773,7 @@ def set_plot_axes(self): # create an equivalency for each flux unit for flux <> flux/pix2. # for similar reasons to the 'untranslatable units' issue, custom - # equivs. can't be combined, so a workaround is creating an eqiv + # equivs. can't be combined, so a workaround is creating an equiv # for each flux that may need an additional equiv. angle_to_pixel_equivs = [_eqv_sb_per_pixel_to_per_angle(un) for un in locally_defined_flux_units] # noqa diff --git a/jdaviz/configs/specviz/plugins/unit_conversion/tests/test_unit_conversion.py b/jdaviz/configs/specviz/plugins/unit_conversion/tests/test_unit_conversion.py index b967e90ffe..51fc06537b 100644 --- a/jdaviz/configs/specviz/plugins/unit_conversion/tests/test_unit_conversion.py +++ b/jdaviz/configs/specviz/plugins/unit_conversion/tests/test_unit_conversion.py @@ -100,7 +100,7 @@ def test_conv_no_data(specviz_helper, spectrum1d): # spectrum not load is in Flux units, sb_unit and flux_unit # should be enabled, spectral_y_type should not be plg = specviz_helper.plugins["Unit Conversion"] - with pytest.raises(ValueError, match="no valid unit choices"): + with pytest.raises(ValueError, match="could not find match in valid x display units"): plg.spectral_unit = "micron" assert len(specviz_helper.app.data_collection) == 0 @@ -290,11 +290,17 @@ def test_contour_unit_conversion(cubeviz_helper, spectrum1d_cube_fluxunit_jy_per # Make sure that the contour values get updated po_plg.contour_visible = True + assert uc_plg.spectral_y_type == 'Flux' + assert uc_plg.flux_unit == 'Jy' + assert uc_plg.sb_unit == "Jy / sr" + assert cubeviz_helper.viewers['flux-viewer']._obj.layers[0].state.attribute_display_unit == "Jy / sr" # noqa assert np.allclose(po_plg.contour_max.value, 199) - uc_plg._obj.spectral_y_type_selected = 'Surface Brightness' + uc_plg.spectral_y_type = 'Surface Brightness' uc_plg.flux_unit = 'MJy' + assert uc_plg.sb_unit == "MJy / sr" + assert cubeviz_helper.viewers['flux-viewer']._obj.layers[0].state.attribute_display_unit == "MJy / sr" # noqa assert np.allclose(po_plg.contour_max.value, 1.99e-4) diff --git a/jdaviz/configs/specviz/plugins/unit_conversion/unit_conversion.py b/jdaviz/configs/specviz/plugins/unit_conversion/unit_conversion.py index 4a287d4123..562dab80c3 100644 --- a/jdaviz/configs/specviz/plugins/unit_conversion/unit_conversion.py +++ b/jdaviz/configs/specviz/plugins/unit_conversion/unit_conversion.py @@ -69,6 +69,9 @@ class UnitConversion(PluginTemplateMixin): derived from the set values of ``flux_unit`` and ``angle_unit``. * ``spectral_y_type`` (:class:`~jdaviz.core.template_mixin.SelectPluginComponent`): Select the y-axis physical type for the spectrum-viewer (applicable only to Cubeviz). + * ``spectral_y_unit``: Read-only property for the current y-axis unit in the spectrum-viewer, + either ``flux_unit`` or ``sb_unit`` depending on the selected ``spectral_y_type`` + (applicable only to Cubeviz). """ template_file = __file__, "unit_conversion.vue" @@ -161,7 +164,7 @@ def user_api(self): if self.has_time: expose += ['time_unit'] if self.config == 'cubeviz': - expose += ['spectral_y_type'] + expose += ['spectral_y_type', 'spectral_y_unit'] return PluginUserApi(self, expose=expose, readonly=readonly) @property @@ -170,6 +173,10 @@ def sb_unit(self): # (rather than exposing a select object) return self.sb_unit_selected + @property + def spectral_y_unit(self): + return self.sb_unit_selected if self.spectral_y_type_selected == 'Surface Brightness' else self.flux_unit_selected # noqa + def _on_add_data_to_viewer(self, msg): # toggle warning message for cubes without PIXAR_SR defined if self.config == 'cubeviz': @@ -182,10 +189,10 @@ def _on_add_data_to_viewer(self, msg): viewer = msg.viewer - if not (len(self.spectral_unit_selected) - and len(self.flux_unit_selected) - and len(self.angle_unit_selected) - and (self.config == 'cubeviz' and not len(self.spectral_y_type_selected))): + if (not len(self.spectral_unit_selected) + or not len(self.flux_unit_selected) + or not len(self.angle_unit_selected) + or (self.config == 'cubeviz' and not len(self.spectral_y_type_selected))): data_obj = msg.data.get_object() if isinstance(data_obj, Spectrum1D): @@ -240,11 +247,11 @@ def _on_add_data_to_viewer(self, msg): # or handle other cases for ramp profile viewers if isinstance(viewer, JdavizProfileView): if (viewer.state.x_display_unit == self.spectral_unit_selected - and viewer.state.y_display_unit == self.app._get_display_unit('spectral_y')): + and viewer.state.y_display_unit == self.spectral_y_unit): # data already existed in this viewer and display units were already set return - # this spectral viewer was empty (did not have display units set yet), + # this spectral viewer was empty (did not have display units set yet),˜ # but global selections are available in the plugin, # so we'll set them to the viewer here viewer.state.x_display_unit = self.spectral_unit_selected @@ -279,8 +286,9 @@ def _on_unit_selected(self, msg): elif axis == 'flux': if len(self.angle_unit_selected): # NOTE: setting sb_unit_selected will call this method again with axis=='sb', - # which in turn will call _handle_spectral_y_unit and - # send a second GlobalDisplayUnitChanged message for sb + # which in turn will call _handle_attribute_display_unit, + # _handle_spectral_y_unit (if spectral_y_type_selected == 'Surface Brightness'), + # and send a second GlobalDisplayUnitChanged message for sb self.sb_unit_selected = _flux_to_sb_unit(self.flux_unit.selected, self.angle_unit.selected) @@ -289,8 +297,10 @@ def _on_unit_selected(self, msg): elif axis == 'angle': if len(self.flux_unit_selected): - # NOTE: setting sb_unit_selected will call this method again and - # send a second GlobalDisplayUnitChanged message for sb + # NOTE: setting sb_unit_selected will call this method again with axis=='sb', + # which in turn will call _handle_attribute_display_unit, + # _handle_spectral_y_unit (if spectral_y_type_selected == 'Surface Brightness'), + # and send a second GlobalDisplayUnitChanged message for sb self.sb_unit_selected = _flux_to_sb_unit(self.flux_unit.selected, self.angle_unit.selected) @@ -315,9 +325,9 @@ def _handle_spectral_y_unit(self, *args): the spectrum viewer with the new unit, and then emit a GlobalDisplayUnitChanged message to notify """ - yunit_selected = self.sb_unit_selected if self.spectral_y_type_selected == 'Surface Brightness' else self.flux_unit_selected # noqa - yunit = _valid_glue_display_unit(yunit_selected, self.spectrum_viewer, 'y') + yunit = _valid_glue_display_unit(self.spectral_y_unit, self.spectrum_viewer, 'y') if self.spectrum_viewer.state.y_display_unit == yunit: + self.spectrum_viewer.set_plot_axes() return try: self.spectrum_viewer.state.y_display_unit = yunit @@ -346,7 +356,10 @@ def _handle_attribute_display_unit(self, attr_unit, layers=None): # DQ layer doesn't play nicely with this attribute if "DQ" in layer.layer.label or isinstance(layer.layer, GroupedSubset): continue - elif u.Unit(layer.layer.get_component("flux").units).physical_type != 'surface brightness': # noqa + elif ("flux" not in [str(c) for c in layer.layer.components] + or u.Unit(layer.layer.get_component("flux").units).physical_type != 'surface brightness'): # noqa continue - if hasattr(layer, 'attribute_display_unit'): - layer.attribute_display_unit = attr_unit + if hasattr(layer.state, 'attribute_display_unit'): + layer.state.attribute_display_unit = _valid_glue_display_unit(attr_unit, + layer, + 'attribute')