I’m still mulling over how to get the Yaesu-defined preset (broadcast) memory addresses into the Yaesu drivers. These are NOT amateur frequencies, but some of general listening interest such as weather, VHF marine and HF AM broadcasts, especially good for radios that can receive more than the amateur bands.These presets are NOT mutable, or in the accessible memory image, and can only be accessed by front panel or referenced in the memory banks (they can be referred to in a bank, along with “regular” memories. The presets have one of three high bits set in the memory number.) In fact, a Yaesu radio user has included a weather station in one of his banks which caused a problem when CHIRP read the radio. The drivers have a workaround of sorts for now. AFAICT, the Yaesu documentation shows the same set of presets for multiple radios.
I’ve now found the sub_devices settings, and see several drivers that use them. Since the sub_devices seem to display a Memory and Banks tab for each variant, they’d essentially be perfect:
there could be a “normal” variant that works the way it does presently, and a “presets” variant that only displays the data for the Yaesu-defined preset addresses. Since the driver is implementing the banks model, it should be able to handle both cases easily, and the preset memories could be marked as immutable.
To start an implementation, it appears that one needs to:
0) NOT change the VARIANT definition. I thought VARIANT was being used to denote versions of the radio type (e.g. FT-1DR vs FT-1DE) rather than sub-devices. Thus most of the Yaesu drivers I’ve worked on have been overriding the value to one specific to Yaesu. Bzzzzt! wrong!
1) set the radio feature has_sub_devices= True
2) add a new class for each sub_device. E.g. add to my Radio class
@directory.register
class Radio(chirp.common.CloneModeRadio):
class Radio_subA(Radio):
VARIANT = ’Sub A'
class Radio_subB(Radio):
VARIANT = ’Sub B'
3) The VARIANT is pre-defined in chirp_common.py as a null string ‘’. Each sub will redefine it as a new string, which will be appended in parentheses to the Memory and Banks tabs.
4) Each sub-device can have new methods to replace (or augment) the previously-defined methods. It appears that one of the methods that’s required is a new get_features() that turns off the “has_sub_devices”. Is this required?
5) Add a method to the driver’s registered class
def get_sub_devices(self):0
if not VARIANT:
return [Radio_subA(self._mmap), Radio_subB(self._mmap)]
else:
return []
This effectively has CHIRP “call” each sub-class into use, and returns a null list when called inside each sub_class. My big question: why is each sub-class “called” with self._mmap as a “parameter”? How IS the “parameter” to be used in the sub-class? I would have thought that parameter should just be self, the way it's used throughout the Radio class. Furthermore, several existing drivers send other objects through this “parameter” … what gives?
I realize that for the ft1d driver (which is inherited for several other radios) this will be too simple. But, for a template.py “radio", a minimal implementation with only two entries in the B sub-radio now looks like the following, and “works” as expected*:
@directory.register
class TemplateRadio(chirp.common.CloneModeRadio):
.
.
.
def get_sub_devices(self):
if not VARIANT:
return [Radio_subA(self._mmap), Radio_subB(self._mmap)]
else:
return []
class Radio_subA(Radio):
VARIANT = ’Sub A’
def get_features(self):
rf = TemplateRadio.get_features(self) # ensure the top class features are set
rf.has_sub_devices = False
return rf
class Radio_subB(Radio):
VARIANT = ’Sub B'
def get_features(self):
rf = TemplateRadio.get_features(self)
rf.has_sub_devices = False
rf.memory_bounds = [0, 2]
return rf.
These are derived from observations of other drivers. Here’s a summary of questions:
- Does the features sub_devices have to be changed to false? I figure I should call the immediate parent get_features() rather than the one from the ft1d, so super should be involved, right?
- What SHOULD the passed parameter be? I’m pretty sure a null parameter doesn’t work.
- If I wanted to implement this in ft1d.py for all radios that subclass from it, what considerations should I make in coding?
- Would it make sense to try to fit this into YaesuCloneModeRadio? Or would it make sense as a hypothetical adjunct to that class such as a new class YaesuPresetsRadio, so that a radio could inherit from both classes to get this functionality (I presume the second sub-radio would ONLY define handle the presets, which would be common to several Yaesu radios, and be defined in the new class.)
* Template.py does need to be changed to allow this: the directory line uncommented, and it also needs from chirp import directory .