From ce48892173f908b8f6ee90bfaac43436f23649e7 Mon Sep 17 00:00:00 2001 From: Jakob Ketterl Date: Mon, 8 Feb 2021 01:16:02 +0100 Subject: [PATCH] make dropdowns work with enums directly --- owrx/controllers/settings.py | 11 ++----- owrx/form/__init__.py | 56 ++++++++++++++++++------------------ 2 files changed, 31 insertions(+), 36 deletions(-) diff --git a/owrx/controllers/settings.py b/owrx/controllers/settings.py index 352f56d..def68a9 100644 --- a/owrx/controllers/settings.py +++ b/owrx/controllers/settings.py @@ -14,11 +14,9 @@ from owrx.form import ( Js8ProfileCheckboxInput, ReceiverKeysConverter, WfmTauValues, - WfmTauConverter, MultiCheckboxInput, OptionalConverter, AprsBeaconSymbols, - EnumConverter, AprsAntennaDirections, ) from urllib.parse import quote @@ -173,8 +171,7 @@ class GeneralSettingsController(AdminController): DropdownInput( "wfm_deemphasis_tau", "Tau setting for WFM (broadcast FM) deemphasis", - options=[o.toOption() for o in WfmTauValues], - converter=WfmTauConverter(), + WfmTauValues, infotext='See ' + "this Wikipedia article for more information", ), @@ -276,8 +273,7 @@ class GeneralSettingsController(AdminController): DropdownInput( "aprs_igate_symbol", "APRS beacon symbol", - [o.toOption() for o in AprsBeaconSymbols], - converter=EnumConverter(AprsBeaconSymbols), + AprsBeaconSymbols, ), TextInput( "aprs_igate_comment", @@ -301,8 +297,7 @@ class GeneralSettingsController(AdminController): DropdownInput( "aprs_igate_dir", "Antenna direction", - [o.toOption() for o in AprsAntennaDirections], - converter=EnumConverter(AprsAntennaDirections), + AprsAntennaDirections ), ), Section( diff --git a/owrx/form/__init__.py b/owrx/form/__init__.py index af529d3..551ea41 100644 --- a/owrx/form/__init__.py +++ b/owrx/form/__init__.py @@ -283,8 +283,17 @@ class Js8ProfileCheckboxInput(MultiCheckboxInput): class DropdownInput(Input): def __init__(self, id, label, options, infotext=None, converter: Converter = None): + try: + isEnum = issubclass(options, DropdownEnum) + except TypeError: + isEnum = False + if isEnum: + self.options = [o.toOption() for o in options] + if converter is None: + converter = EnumConverter(options) + else: + self.options = options super().__init__(id, label, infotext=infotext, converter=converter) - self.options = options def render_input(self, value): return """ @@ -307,20 +316,7 @@ class DropdownInput(Input): return "".join(options) -class WfmTauValues(Enum): - TAU_50_MICRO = (50, "most regions") - TAU_75_MICRO = (75, "Americas and South Korea") - - def __new__(cls, *args, **kwargs): - value, description = args - obj = object.__new__(cls) - obj._value_ = value - obj.description = description - return obj - - def __str__(self): - return "{}µs ({})".format(self.value, self.description) - +class DropdownEnum(Enum): def toOption(self): return Option(self.name, str(self)) @@ -336,15 +332,22 @@ class EnumConverter(Converter): return self.enumCls[value].value -class WfmTauConverter(Converter): - def convert_to_form(self, value): - return WfmTauValues(value * 1e6).name +class WfmTauValues(DropdownEnum): + TAU_50_MICRO = (50e-6, "most regions") + TAU_75_MICRO = (75e-6, "Americas and South Korea") - def convert_from_form(self, value): - return WfmTauValues[value].value / 1e6 + def __new__(cls, *args, **kwargs): + value, description = args + obj = object.__new__(cls) + obj._value_ = value + obj.description = description + return obj + + def __str__(self): + return "{}µs ({})".format(int(self.value * 1E6), self.description) -class AprsBeaconSymbols(Enum): +class AprsBeaconSymbols(DropdownEnum): BEACON_RECEIVE_ONLY = ("R&", "Receive only IGate") BEACON_HF_GATEWAY = ("/&", "HF Gateway") BEACON_IGATE_GENERIC = ("I&", "Igate Generic (please use more specific overlay)") @@ -361,13 +364,10 @@ class AprsBeaconSymbols(Enum): return obj def __str__(self): - return self.description - - def toOption(self): - return Option(self.name, "{description} ({symbol})".format(description=str(self), symbol=self.value)) + return "{description} ({symbol})".format(description=self.description, symbol=self.value) -class AprsAntennaDirections(Enum): +class AprsAntennaDirections(DropdownEnum): DIRECTION_OMNI = None DIRECTION_N = "N" DIRECTION_NE = "NE" @@ -378,5 +378,5 @@ class AprsAntennaDirections(Enum): DIRECTION_W = "W" DIRECTION_NW = "NW" - def toOption(self): - return Option(self.name, "omnidirectional" if self.value is None else self.value) + def __str__(self): + return "omnidirectional" if self.value is None else self.value