diff --git a/python/plugins/processing/algs/grass7/Grass7Algorithm.py b/python/plugins/processing/algs/grass7/Grass7Algorithm.py index 6f9a29fa546..9def6636041 100644 --- a/python/plugins/processing/algs/grass7/Grass7Algorithm.py +++ b/python/plugins/processing/algs/grass7/Grass7Algorithm.py @@ -426,7 +426,7 @@ class Grass7Algorithm(GeoAlgorithm): command += ' ' + param.name elif isinstance(param, ParameterSelection): idx = int(param.value) - command += ' ' + param.name + '=' + str(param.options[idx]) + command += ' ' + param.name + '=' + str(param.options[idx][1]) elif isinstance(param, ParameterString): command += ' ' + param.name + '="' + str(param.value) + '"' elif isinstance(param, ParameterPoint): diff --git a/python/plugins/processing/algs/otb/OTBAlgorithm.py b/python/plugins/processing/algs/otb/OTBAlgorithm.py index 237c3cbd670..0d519d261bb 100644 --- a/python/plugins/processing/algs/otb/OTBAlgorithm.py +++ b/python/plugins/processing/algs/otb/OTBAlgorithm.py @@ -276,7 +276,7 @@ class OTBAlgorithm(GeoAlgorithm): elif isinstance(param, ParameterSelection): commands.append(param.name) idx = int(param.value) - commands.append(str(param.options[idx])) + commands.append(str(param.options[idx][1])) elif isinstance(param, ParameterBoolean): if param.value: commands.append(param.name) diff --git a/python/plugins/processing/core/parameters.py b/python/plugins/processing/core/parameters.py index 8f822e3af80..72d191fedd8 100644 --- a/python/plugins/processing/core/parameters.py +++ b/python/plugins/processing/core/parameters.py @@ -1061,18 +1061,25 @@ class ParameterSelection(Parameter): elif isinstance(self.options, str): self.options = self.options.split(";") + # compute options as (value, text) + options = [] + for i, option in enumerate(self.options): + if option is None or isinstance(option, basestring): + options.append((i, option)) + else: + options.append((option[0], option[1])) + self.options = options + self.values = [option[0] for option in options] + + self.value = None if default is not None: - try: - self.default = int(default) - except: - self.default = 0 - self.value = self.default + self.setValue(self.default) def setValue(self, value): if value is None: if not self.optional: return False - self.value = 0 + self.value = None return True if isinstance(value, list): @@ -1080,22 +1087,32 @@ class ParameterSelection(Parameter): return False values = [] for v in value: + if v in self.values: + values.append(v) + continue try: - n = int(v) - values.append(n) + v = int(v) except: + pass + if not v in self.values: return False + values.append(v) if not self.optional and len(values) == 0: return False self.value = values return True else: - try: - n = int(value) - self.value = n + if value in self.values: + self.value = value return True + try: + value = int(value) except: + pass + if not value in self.values: return False + self.value = value + return True @classmethod def fromScriptCode(self, line): diff --git a/python/plugins/processing/gui/MultipleInputDialog.py b/python/plugins/processing/gui/MultipleInputDialog.py index 41fc035d85d..bd668586e04 100644 --- a/python/plugins/processing/gui/MultipleInputDialog.py +++ b/python/plugins/processing/gui/MultipleInputDialog.py @@ -68,9 +68,10 @@ class MultipleInputDialog(BASE, WIDGET): def populateList(self): model = QStandardItemModel() - for i, option in enumerate(self.options): - item = QStandardItem(option) - item.setCheckState(Qt.Checked if i in self.selectedoptions else Qt.Unchecked) + for value, text in self.options: + item = QStandardItem(text) + item.setData(value, Qt.UserRole) + item.setCheckState(Qt.Checked if value in self.selectedoptions else Qt.Unchecked) item.setCheckable(True) model.appendRow(item) @@ -82,7 +83,7 @@ class MultipleInputDialog(BASE, WIDGET): for i in range(model.rowCount()): item = model.item(i) if item.checkState() == Qt.Checked: - self.selectedoptions.append(i) + self.selectedoptions.append(item.data(Qt.UserRole)) QDialog.accept(self) def reject(self): diff --git a/python/plugins/processing/gui/wrappers.py b/python/plugins/processing/gui/wrappers.py index 7cdff13a281..421919ec8f0 100644 --- a/python/plugins/processing/gui/wrappers.py +++ b/python/plugins/processing/gui/wrappers.py @@ -652,22 +652,23 @@ class SelectionWidgetWrapper(WidgetWrapper): return MultipleInputPanel(options=self.param.options) else: widget = QComboBox() - widget.addItems(self.param.options) + for option in self.param.options: + widget.addItem(option[1], option[0]) if self.param.default: - widget.setCurrentIndex(self.param.default) + widget.setCurrentIndex(widget.findData(self.param.default)) return widget def setValue(self, value): if self.param.multiple: self.widget.setSelectedItems(value) else: - self.widget.setCurrentIndex(int(value)) + self.widget.setCurrentIndex(self.widget.findData(value)) def value(self): if self.param.multiple: return self.widget.selectedoptions else: - return self.widget.currentIndex() + return self.widget.currentData() class VectorWidgetWrapper(WidgetWrapper): diff --git a/python/plugins/processing/tests/ParametersTest.py b/python/plugins/processing/tests/ParametersTest.py index 5da37bd965d..7643b3e6f3f 100644 --- a/python/plugins/processing/tests/ParametersTest.py +++ b/python/plugins/processing/tests/ParametersTest.py @@ -272,7 +272,7 @@ class ParameterSelectionTest(unittest.TestCase): parameter = ParameterSelection('myName', 'myDesc', ['option1', 'option2', 'option3'], default=0.0) self.assertEqual(parameter.value, 0) parameter = ParameterSelection('myName', 'myDesc', ['option1', 'option2', 'option3'], default='a') - self.assertEqual(parameter.value, 0) + self.assertEqual(parameter.value, None) def testOptional(self): optionalParameter = ParameterSelection('myName', 'myDesc', ['option1', 'option2', 'option3'], default=0, optional=True) @@ -280,7 +280,7 @@ class ParameterSelectionTest(unittest.TestCase): optionalParameter.setValue(1) self.assertEqual(optionalParameter.value, 1) self.assertTrue(optionalParameter.setValue(None)) - self.assertEqual(optionalParameter.value, 0) + self.assertEqual(optionalParameter.value, None) requiredParameter = ParameterSelection('myName', 'myDesc', ['option1', 'option2', 'option3'], default=0, optional=False) self.assertEqual(requiredParameter.value, 0) @@ -289,6 +289,22 @@ class ParameterSelectionTest(unittest.TestCase): self.assertFalse(requiredParameter.setValue(None)) self.assertEqual(requiredParameter.value, 1) + def testTupleOptions(self): + options = ( + ('o1', 'option1'), + ('o2', 'option2'), + ('o3', 'option3')) + + optionalParameter = ParameterSelection('myName', 'myDesc', options, default='o1') + self.assertEqual(optionalParameter.value, 'o1') + optionalParameter.setValue('o2') + self.assertEqual(optionalParameter.value, 'o2') + + optionalParameter = ParameterSelection('myName', 'myDesc', options, default=['o1', 'o2'], multiple=True) + self.assertEqual(optionalParameter.value, ['o1', 'o2']) + optionalParameter.setValue(['o2']) + self.assertEqual(optionalParameter.value, ['o2']) + class ParameterFileTest(unittest.TestCase):