diff --git a/apps/osmocom_siggen b/apps/osmocom_siggen index be97598..a290b53 100755 --- a/apps/osmocom_siggen +++ b/apps/osmocom_siggen @@ -314,6 +314,130 @@ class app_gui(pubsub): except RuntimeError: pass + ################################################## + # DC Offset controls + ################################################## + + dc_offset_vbox = forms.static_box_sizer(parent=self.panel, + label="DC Offset Correction", + orient=wx.VERTICAL, + bold=True) + dc_offset_vbox.AddSpacer(3) + # First row of sample rate controls + dc_offset_hbox = wx.BoxSizer(wx.HORIZONTAL) + dc_offset_vbox.Add(dc_offset_hbox, 0, wx.EXPAND) + dc_offset_vbox.AddSpacer(3) + + # Add frequency controls to top window sizer + self.vbox.Add(dc_offset_vbox, 0, wx.EXPAND) + self.vbox.AddSpacer(3) + + dc_offset_hbox.AddSpacer(3) + forms.text_box( + parent=self.panel, sizer=dc_offset_hbox, + label='Real', + proportion=1, + converter=forms.float_converter(), + ps=self.tb, + key=osmocom_siggen.DC_OFFSET_REAL + ) + dc_offset_hbox.AddSpacer(3) + + forms.slider( + parent=self.panel, sizer=dc_offset_hbox, + proportion=3, + minimum=-1, + maximum=+1, + step_size=0.001, + ps=self.tb, + key=osmocom_siggen.DC_OFFSET_REAL + ) + dc_offset_hbox.AddSpacer(3) + + dc_offset_hbox.AddSpacer(3) + forms.text_box( + parent=self.panel, sizer=dc_offset_hbox, + label='Imag', + proportion=1, + converter=forms.float_converter(), + ps=self.tb, + key=osmocom_siggen.DC_OFFSET_IMAG + ) + dc_offset_hbox.AddSpacer(3) + + forms.slider( + parent=self.panel, sizer=dc_offset_hbox, + proportion=3, + minimum=-1, + maximum=+1, + step_size=0.001, + ps=self.tb, + key=osmocom_siggen.DC_OFFSET_IMAG + ) + dc_offset_hbox.AddSpacer(3) + + ################################################## + # IQ Imbalance controls + ################################################## + + iq_balance_vbox = forms.static_box_sizer(parent=self.panel, + label="IQ Imbalance Correction", + orient=wx.VERTICAL, + bold=True) + iq_balance_vbox.AddSpacer(3) + # First row of sample rate controls + iq_balance_hbox = wx.BoxSizer(wx.HORIZONTAL) + iq_balance_vbox.Add(iq_balance_hbox, 0, wx.EXPAND) + iq_balance_vbox.AddSpacer(3) + + # Add frequency controls to top window sizer + self.vbox.Add(iq_balance_vbox, 0, wx.EXPAND) + self.vbox.AddSpacer(3) + + iq_balance_hbox.AddSpacer(3) + forms.text_box( + parent=self.panel, sizer=iq_balance_hbox, + label='Mag', + proportion=1, + converter=forms.float_converter(), + ps=self.tb, + key=osmocom_siggen.IQ_BALANCE_MAG + ) + iq_balance_hbox.AddSpacer(3) + + forms.slider( + parent=self.panel, sizer=iq_balance_hbox, + proportion=3, + minimum=-1, + maximum=+1, + step_size=0.001, + ps=self.tb, + key=osmocom_siggen.IQ_BALANCE_MAG + ) + iq_balance_hbox.AddSpacer(3) + + iq_balance_hbox.AddSpacer(3) + forms.text_box( + parent=self.panel, sizer=iq_balance_hbox, + label='Phase', + proportion=1, + converter=forms.float_converter(), + ps=self.tb, + key=osmocom_siggen.IQ_BALANCE_PHA + ) + iq_balance_hbox.AddSpacer(3) + + forms.slider( + parent=self.panel, sizer=iq_balance_hbox, + proportion=3, + minimum=-1, + maximum=+1, + step_size=0.001, + ps=self.tb, + key=osmocom_siggen.IQ_BALANCE_PHA + ) + iq_balance_hbox.AddSpacer(3) + ################################################## # Sample Rate controls ################################################## diff --git a/apps/osmocom_siggen_base.py b/apps/osmocom_siggen_base.py index 6dcbc6d..f7f5854 100644 --- a/apps/osmocom_siggen_base.py +++ b/apps/osmocom_siggen_base.py @@ -33,6 +33,10 @@ WAVEFORM2_FREQ_KEY = 'waveform2_freq' FREQ_RANGE_KEY = 'freq_range' GAIN_RANGE_KEY = lambda x: 'gain_range:'+x BWIDTH_RANGE_KEY = 'bwidth_range' +DC_OFFSET_REAL = 'dc_offset_real' +DC_OFFSET_IMAG = 'dc_offset_imag' +IQ_BALANCE_MAG = 'iq_balance_mag' +IQ_BALANCE_PHA = 'iq_balance_pha' TYPE_KEY = 'type' def setter(ps, key, val): ps[key] = val @@ -143,6 +147,12 @@ class top_block(gr.top_block, pubsub): self[WAVEFORM_OFFSET_KEY] = options.offset self[WAVEFORM2_FREQ_KEY] = options.waveform2_freq + # initialize reasonable defaults for DC / IQ correction + self[DC_OFFSET_REAL] = 0 + self[DC_OFFSET_IMAG] = 0 + self[IQ_BALANCE_MAG] = 0 + self[IQ_BALANCE_PHA] = 0 + #subscribe set methods self.subscribe(SAMP_RATE_KEY, self.set_samp_rate) @@ -157,6 +167,11 @@ class top_block(gr.top_block, pubsub): self.subscribe(WAVEFORM2_FREQ_KEY, self.set_waveform2_freq) self.subscribe(TYPE_KEY, self.set_waveform) + self.subscribe(DC_OFFSET_REAL, self.set_dc_offset) + self.subscribe(DC_OFFSET_IMAG, self.set_dc_offset) + self.subscribe(IQ_BALANCE_MAG, self.set_iq_balance) + self.subscribe(IQ_BALANCE_PHA, self.set_iq_balance) + #force update on pubsub keys for key in (SAMP_RATE_KEY, GAIN_KEY, BWIDTH_KEY, TX_FREQ_KEY, FREQ_CORR_KEY, AMPLITUDE_KEY, @@ -248,6 +263,28 @@ class top_block(gr.top_block, pubsub): if self._verbose: print "Set bandwidth to:", bw + def set_dc_offset(self, value): + correction = complex( self[DC_OFFSET_REAL], self[DC_OFFSET_IMAG] ) + + try: + self._sink.set_dc_offset( correction ) + + if self._verbose: + print "Set DC offset to", correction + except RuntimeError as ex: + print ex + + def set_iq_balance(self, value): + correction = complex( self[IQ_BALANCE_MAG], self[IQ_BALANCE_PHA] ) + + try: + self._sink.set_iq_balance( correction ) + + if self._verbose: + print "Set IQ balance to", correction + except RuntimeError as ex: + print ex + def set_freq(self, freq): if freq is None: f = self[FREQ_RANGE_KEY]