wip: #34 - finishes the airspy tuner editor panel and adds tuner info

button to the r820t tuner editor to view serial number and misc info.
This commit is contained in:
denny
2016-03-19 14:49:55 -04:00
parent a4d69ce0aa
commit 6bb417f69a
8 changed files with 800 additions and 899 deletions

View File

@@ -100,6 +100,7 @@ public class TunerEditor extends Editor<Tuner>
listPanel.add( tableScroller, "span" );
mNewConfigurationButton.setEnabled( false );
mNewConfigurationButton.setToolTipText( "Create a new configuration for the currently selected tuner" );
mNewConfigurationButton.addActionListener( new ActionListener()
{
@Override
@@ -120,6 +121,7 @@ public class TunerEditor extends Editor<Tuner>
listPanel.add( mNewConfigurationButton );
mDeleteConfigurationButton.setEnabled( false );
mDeleteConfigurationButton.setToolTipText( "Deletes the currently selected tuner" );
mDeleteConfigurationButton.addActionListener( new ActionListener()
{
@Override
@@ -140,6 +142,7 @@ public class TunerEditor extends Editor<Tuner>
listPanel.add( mDeleteConfigurationButton );
mAssignConfigurationButton.setEnabled( false );
mAssignConfigurationButton.setToolTipText( "Assigns to the currently selected tuner configuration to the selected tuner" );
mAssignConfigurationButton.addActionListener( new ActionListener()
{
@Override

View File

@@ -1,77 +0,0 @@
package source.tuner.airspy;
/*******************************************************************************
* SDR Trunk
* Copyright (C) 2015 Dennis Sheirer
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>
******************************************************************************/
import javax.swing.JLabel;
import javax.swing.JPanel;
import net.miginfocom.swing.MigLayout;
public class AirspyInformationPanel extends JPanel
{
private static final long serialVersionUID = 1L;
private AirspyTunerController mController;
/**
* Displays Airspy firmware, serial number and part identifier
*/
public AirspyInformationPanel( AirspyTunerController controller )
{
mController = controller;
initGUI();
}
private void initGUI()
{
setLayout( new MigLayout( "fill,wrap 2",
"[right,grow][grow]",
"[][][][][grow]" ) );
AirspyDeviceInformation info = mController.getDeviceInfo();
add( new JLabel( "Serial:" ) );
add( new JLabel( info.getSerialNumber() ) );
add( new JLabel( "Firmware:" ) );
//Split the firmware on spaces and use first value -- expose full
//string in a tool tip
String[] firmware = info.getVersion().split( " " );
JLabel firmwareLabel;
if( firmware.length > 1 )
{
firmwareLabel = new JLabel( firmware[ 0 ] );
}
else
{
firmwareLabel = new JLabel( info.getVersion() );
}
firmwareLabel.setToolTipText( info.getVersion() );
add( firmwareLabel );
add( new JLabel( "Part:" ) );
add( new JLabel( info.getPartNumber() ) );
add( new JLabel( "Board ID:" ) );
add( new JLabel( info.getBoardID().getLabel() ) );
}
}

View File

@@ -1,695 +0,0 @@
/*******************************************************************************
* SDR Trunk
* Copyright (C) 2014 Dennis Sheirer
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>
******************************************************************************/
package source.tuner.airspy;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.FocusEvent;
import java.awt.event.FocusListener;
import java.util.List;
import javax.swing.ComboBoxModel;
import javax.swing.DefaultComboBoxModel;
import javax.swing.JButton;
import javax.swing.JCheckBox;
import javax.swing.JComboBox;
import javax.swing.JLabel;
import javax.swing.JOptionPane;
import javax.swing.JPanel;
import javax.swing.JSeparator;
import javax.swing.JSlider;
import javax.swing.JTextField;
import javax.swing.event.ChangeEvent;
import javax.swing.event.ChangeListener;
import javax.usb.UsbException;
import net.miginfocom.swing.MigLayout;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.usb4java.LibUsbException;
import settings.SettingsManager;
import source.SourceException;
import source.tuner.airspy.AirspyTunerController.Gain;
import source.tuner.airspy.AirspyTunerController.GainMode;
public class AirspyTunerConfigurationPanel extends JPanel
{
private final static Logger mLog =
LoggerFactory.getLogger( AirspyTunerConfigurationPanel.class );
private static final long serialVersionUID = 1L;
private SettingsManager mSettingsManager;
private AirspyTunerController mController;
private AirspyTunerConfiguration mSelectedConfig;
private JButton mNewConfiguration;
private JButton mDeleteConfiguration;
private JComboBox<AirspyTunerConfiguration> mComboConfigurations;
private JTextField mName;
private JComboBox<AirspySampleRate> mSampleRateCombo;
private JComboBox<GainMode> mGainModeCombo;
private JLabel mGainLabel;
private JLabel mGainFillerLabel;
private JLabel mGainValueLabel;
private JSlider mGain;
private JLabel mIFGainLabel;
private JLabel mIFGainFillerLabel;
private JLabel mIFGainValueLabel;
private JSlider mIFGain;
private JLabel mLNAGainLabel;
private JCheckBox mLNAAGC;
private JLabel mLNAGainValueLabel;
private JSlider mLNAGain;
private JLabel mMixerGainValueLabel;
private JCheckBox mMixerAGC;
private JLabel mMixerGainLabel;
private JSlider mMixerGain;
public AirspyTunerConfigurationPanel( SettingsManager settingsManager,
AirspyTunerController controller )
{
mSettingsManager = settingsManager;
mController = controller;
init();
}
/**
* Initializes the gui components
*/
private void init()
{
setLayout( new MigLayout( "fill,wrap 4", "[left][grow][grow][right]",
"[][][][][][][grow]" ) );
/**
* Tuner configuration selector
*/
mComboConfigurations = new JComboBox<AirspyTunerConfiguration>();
mComboConfigurations.setModel( getModel() );
/* Determine which tuner configuration should be selected/displayed */
// TunerConfigurationAssignment savedConfig = null;
String serial = null;
serial = mController.getDeviceInfo().getSerialNumber();
if( serial != null )
{
// savedConfig = mSettingsManager.getSelectedTunerConfiguration(
// TunerType.AIRSPY_R820T, serial );
}
// if( savedConfig != null )
// {
// mSelectedConfig = getNamedConfiguration(
// savedConfig.getTunerConfigurationName() );
// }
/* If we couldn't determine the saved/selected config, use the first one */
if( mSelectedConfig == null )
{
mSelectedConfig = mComboConfigurations.getItemAt( 0 );
//Store this config as the default for this tuner at this address
if( serial != null )
{
// mSettingsManager.setSelectedTunerConfiguration( TunerType.AIRSPY_R820T,
// serial, mSelectedConfig );
}
}
mComboConfigurations.setSelectedItem( mSelectedConfig );
mComboConfigurations.addActionListener( new ActionListener()
{
@Override
public void actionPerformed( ActionEvent e )
{
AirspyTunerConfiguration selected =
(AirspyTunerConfiguration)mComboConfigurations
.getItemAt( mComboConfigurations.getSelectedIndex() );
if( selected != null )
{
update( selected );
}
}
});
add( new JLabel( "Config:" ) );
add( mComboConfigurations, "span,growx,push" );
add( new JSeparator(), "span,growx,push" );
/**
* Tuner Configuration Name
*/
mName = new JTextField();
mName.setText( mSelectedConfig.getName() );
mName.addFocusListener( new FocusListener()
{
@Override
public void focusLost( FocusEvent e )
{
mSelectedConfig.setName( mName.getText() );
save();
}
@Override
public void focusGained( FocusEvent e ) {}
} );
add( new JLabel( "Name:" ) );
add( mName, "span,growx,push" );
/**
* Sample Rate
*/
add( new JLabel( "Sample Rate:" ) );
List<AirspySampleRate> rates = mController.getSampleRates();
mSampleRateCombo = new JComboBox<AirspySampleRate>(
new DefaultComboBoxModel<AirspySampleRate>( rates.toArray(
new AirspySampleRate[ rates.size() ] ) ) );
mSampleRateCombo.setSelectedItem( mController.getSampleRate() );
mSampleRateCombo.addActionListener( new ActionListener()
{
@Override
public void actionPerformed( ActionEvent e )
{
AirspySampleRate rate = (AirspySampleRate)mSampleRateCombo.getSelectedItem();
try
{
mController.setSampleRate( rate );
mSelectedConfig.setSampleRate( rate.getRate() );
save();
}
catch ( LibUsbException | UsbException e1 )
{
JOptionPane.showMessageDialog( AirspyTunerConfigurationPanel.this,
"Couldn't set sample rate to " + rate.getLabel() );
mLog.error( "Error setting airspy sample rate", e1 );
}
}
} );
add( mSampleRateCombo, "span 3,growx" );
add( new JSeparator(), "span,growx,push" );
/**
* Gain Mode
*/
add( new JLabel( "Gain Mode:" ) );
mGainModeCombo = new JComboBox<AirspyTunerController.GainMode>( GainMode.values() );
mGainModeCombo.setSelectedItem( Gain.getGainMode( mSelectedConfig.getGain() ) );
mGainModeCombo.addActionListener( new ActionListener()
{
@Override
public void actionPerformed( ActionEvent e )
{
GainMode mode = (GainMode)mGainModeCombo.getSelectedItem();
updateGainComponents( mode );
switch( mode )
{
case LINEARITY:
mGain.setValue( AirspyTunerController.LINEARITY_GAIN_DEFAULT.getValue() );
mSelectedConfig.setGain( AirspyTunerController.LINEARITY_GAIN_DEFAULT );
break;
case SENSITIVITY:
mGain.setValue( AirspyTunerController.SENSITIVITY_GAIN_DEFAULT.getValue() );
mSelectedConfig.setGain( AirspyTunerController.SENSITIVITY_GAIN_DEFAULT );
break;
case CUSTOM:
default:
mLNAGain.setValue( mSelectedConfig.getLNAGain() );
mMixerGain.setValue( mSelectedConfig.getMixerGain() );
mIFGain.setValue( mSelectedConfig.getIFGain() );
mSelectedConfig.setGain( Gain.CUSTOM );
break;
}
save();
}
} );
add( mGainModeCombo, "wrap" );
/**
* Gain
*/
mGainLabel = new JLabel( "Gain" );
add( mGainLabel );
mGainFillerLabel = new JLabel( "" );
add( mGainFillerLabel, "span 2" );
mGainValueLabel = new JLabel( String.valueOf( mSelectedConfig.getGain().getValue() ) );
add( mGainValueLabel, "wrap" );
mGain = new JSlider( JSlider.HORIZONTAL,
AirspyTunerController.GAIN_MIN,
AirspyTunerController.GAIN_MAX,
mSelectedConfig.getGain().getValue() );
mGain.setMajorTickSpacing( 1 );
mGain.setPaintTicks( true );
mGain.addChangeListener( new ChangeListener()
{
@Override
public void stateChanged( ChangeEvent event )
{
GainMode mode = (GainMode)mGainModeCombo.getSelectedItem();
int value = mGain.getValue();
Gain gain = Gain.getGain( mode, value );
try
{
mController.setGain( gain );
mSelectedConfig.setGain( gain );
save();
mGainValueLabel.setText( String.valueOf( gain.getValue() ) );
}
catch ( Exception e )
{
mLog.error( "Couldn't set airspy gain to:" + gain.name(), e );
JOptionPane.showMessageDialog( mGain,
"Couldn't set gain value to " + gain.getValue() );
mGain.setValue( mSelectedConfig.getGain().getValue() );
}
}
} );
add( mGain, "span,grow" );
/**
* IF/VGA Gain
*/
mIFGainLabel = new JLabel( "IF Gain" );
add( mIFGainLabel );
mIFGainFillerLabel = new JLabel( "" );
add( mIFGainFillerLabel, "span 2" );
mIFGainValueLabel = new JLabel( String.valueOf( mSelectedConfig.getIFGain() ) );
add( mIFGainValueLabel, "wrap" );
mIFGain = new JSlider( JSlider.HORIZONTAL,
AirspyTunerController.IF_GAIN_MIN,
AirspyTunerController.IF_GAIN_MAX,
mSelectedConfig.getIFGain() );
mIFGain.setMajorTickSpacing( 1 );
mIFGain.setPaintTicks( true );
mIFGain.addChangeListener( new ChangeListener()
{
@Override
public void stateChanged( ChangeEvent event )
{
int gain = mIFGain.getValue();
try
{
mController.setIFGain( gain );
mSelectedConfig.setIFGain( gain );
save();
mIFGainValueLabel.setText( String.valueOf( gain ) );
}
catch ( Exception e )
{
mLog.error( "Couldn't set airspy IF gain to:" + gain, e );
JOptionPane.showMessageDialog( mIFGain,
"Couldn't set IF gain value to " + gain );
mIFGain.setValue( mSelectedConfig.getIFGain() );
}
}
} );
add( mIFGain, "span,grow" );
/**
* Mixer Gain
*/
mMixerGainLabel = new JLabel( "Mixer Gain" );
add( mMixerGainLabel );
mMixerAGC = new JCheckBox( "AGC" );
mMixerAGC.setSelected( mSelectedConfig.isMixerAGC() );
mMixerAGC.addActionListener( new ActionListener()
{
@Override
public void actionPerformed( ActionEvent e )
{
try
{
mController.setMixerAGC( !mSelectedConfig.isMixerAGC() );
mSelectedConfig.setMixerAGC( !mSelectedConfig.isMixerAGC() );
save();
}
catch ( Exception e1 )
{
mLog.error( "Error setting Mixer AGC Enabled:" + !mSelectedConfig.isMixerAGC() );
mMixerAGC.setSelected( mSelectedConfig.isMixerAGC() );
}
}
} );
add( mMixerAGC, "span 2,center" );
mMixerGainValueLabel = new JLabel( String.valueOf( mSelectedConfig.getMixerGain() ) );
add( mMixerGainValueLabel, "wrap" );
mMixerGain = new JSlider( JSlider.HORIZONTAL,
AirspyTunerController.MIXER_GAIN_MIN,
AirspyTunerController.MIXER_GAIN_MAX,
mSelectedConfig.getMixerGain() );
mMixerGain.setMajorTickSpacing( 1 );
mMixerGain.setPaintTicks( true );
mMixerGain.addChangeListener( new ChangeListener()
{
@Override
public void stateChanged( ChangeEvent event )
{
int gain = mMixerGain.getValue();
try
{
mController.setMixerGain( gain );
mSelectedConfig.setMixerGain( gain );
save();
mMixerGainValueLabel.setText( String.valueOf( gain ) );
}
catch ( Exception e )
{
mLog.error( "Couldn't set airspy Mixer gain to:" + gain, e );
JOptionPane.showMessageDialog( mIFGain, "Couldn't set Mixer gain value to " + gain );
mMixerGain.setValue( mSelectedConfig.getMixerGain() );
}
}
} );
add( mMixerGain, "span,grow" );
/**
* LNA Gain
*/
mLNAGainLabel = new JLabel( "LNA Gain" );
add( mLNAGainLabel );
mLNAAGC = new JCheckBox( "AGC" );
mLNAAGC.setSelected( mSelectedConfig.isLNAAGC() );
mLNAAGC.addActionListener( new ActionListener()
{
@Override
public void actionPerformed( ActionEvent e )
{
try
{
mController.setLNAAGC( !mSelectedConfig.isLNAAGC() );
mSelectedConfig.setLNAAGC( !mSelectedConfig.isLNAAGC() );
save();
}
catch ( Exception e1 )
{
mLog.error( "Error setting LNA AGC Enabled:" + !mSelectedConfig.isLNAAGC() );
mLNAAGC.setSelected( mSelectedConfig.isLNAAGC() );
}
}
} );
add( mLNAAGC, "span 2,center" );
mLNAGainValueLabel = new JLabel( String.valueOf( mSelectedConfig.getLNAGain() ) );
add( mLNAGainValueLabel, "wrap" );
mLNAGain = new JSlider( JSlider.HORIZONTAL,
AirspyTunerController.LNA_GAIN_MIN,
AirspyTunerController.LNA_GAIN_MAX,
mSelectedConfig.getLNAGain() );
mLNAGain.setMajorTickSpacing( 1 );
mLNAGain.setPaintTicks( true );
mLNAGain.addChangeListener( new ChangeListener()
{
@Override
public void stateChanged( ChangeEvent event )
{
int gain = mLNAGain.getValue();
try
{
mController.setLNAGain( gain );
mSelectedConfig.setLNAGain( gain );
save();
mLNAGainValueLabel.setText( String.valueOf( gain ) );
}
catch ( Exception e )
{
mLog.error( "Couldn't set airspy LNA gain to:" + gain, e );
JOptionPane.showMessageDialog( mIFGain, "Couldn't set LNA gain value to " + gain );
mLNAGain.setValue( mSelectedConfig.getLNAGain() );
}
}
} );
add( mLNAGain, "span,grow" );
//Set the enabled state of each of the gain controls
updateGainComponents( (GainMode)mGainModeCombo.getSelectedItem() );
/**
* Create a new configuration
*/
mNewConfiguration = new JButton( "New" );
mNewConfiguration.addActionListener( new ActionListener()
{
@Override
public void actionPerformed( ActionEvent e )
{
// TunerConfiguration config =
// mSettingsManager.addNewTunerConfiguration(
// TunerType.AIRSPY_R820T,
// "New Configuration" );
//
// mComboConfigurations.setModel( getModel() );
//
// mComboConfigurations.setSelectedItem( config );
//
// repaint();
}
} );
add( mNewConfiguration, "span 2,growx,push" );
/**
* Delete the currently selected configuration
*/
mDeleteConfiguration = new JButton( "Delete" );
mDeleteConfiguration.addActionListener( new ActionListener()
{
@Override
public void actionPerformed( ActionEvent e )
{
AirspyTunerConfiguration selected =
(AirspyTunerConfiguration)mComboConfigurations
.getItemAt( mComboConfigurations.getSelectedIndex() );
if( selected != null )
{
int n = JOptionPane.showConfirmDialog(
AirspyTunerConfigurationPanel.this,
"Are you sure you want to delete '"
+ selected.getName() + "'?",
"Are you sure?",
JOptionPane.YES_NO_OPTION );
if( n == JOptionPane.YES_OPTION )
{
// mSettingsManager.deleteTunerConfiguration( selected );
mComboConfigurations.setModel( getModel() );
mComboConfigurations.setSelectedIndex( 0 );
repaint();
}
}
}
} );
add( mDeleteConfiguration, "span 2,growx,push" );
}
/**
* Updates the enabled state of each of the gain controls according to the
* specified gain mode. The overall gain controls are enabled for linearity
* and sensitivity and the individual gain controls are disabled, and
* vice-versa for custom mode.
*/
private void updateGainComponents( GainMode mode )
{
boolean isCustom = ( mode == GainMode.CUSTOM );
mGainLabel.setEnabled( !isCustom );
mGainFillerLabel.setEnabled( !isCustom );
mGainValueLabel.setEnabled( !isCustom );
mGain.setEnabled( !isCustom );
mIFGainLabel.setEnabled( isCustom );
mIFGainFillerLabel.setEnabled( isCustom );
mIFGainValueLabel.setEnabled( isCustom );
mIFGain.setEnabled( isCustom );
mLNAGainLabel.setEnabled( isCustom );
mLNAAGC.setEnabled( isCustom );
mLNAGainValueLabel.setEnabled( isCustom );
mLNAGain.setEnabled( isCustom );
mMixerGainValueLabel.setEnabled( isCustom );
mMixerAGC.setEnabled( isCustom );
mMixerGainLabel.setEnabled( isCustom );
mMixerGain.setEnabled( isCustom );
}
/**
* Updates gui controls with the values from the tuner configuration
* @param config - tuner configuration
*/
private void update( AirspyTunerConfiguration config )
{
mSelectedConfig = config;
try
{
mController.apply( config );
mName.setText( config.getName() );
AirspySampleRate rate = mController.getSampleRate(
mSelectedConfig.getSampleRate() );
if( rate != null )
{
mSampleRateCombo.setSelectedItem( rate );
}
mIFGain.setValue( mSelectedConfig.getIFGain() );
mMixerGain.setValue( mSelectedConfig.getMixerGain() );
mLNAGain.setValue( mSelectedConfig.getLNAGain() );
mMixerAGC.setSelected( mSelectedConfig.isMixerAGC() );
mLNAAGC.setSelected( mSelectedConfig.isLNAAGC() );
Gain gain = mSelectedConfig.getGain();
mGainModeCombo.setSelectedItem( Gain.getGainMode( gain ) );
mGain.setValue( gain.getValue() );
// mSettingsManager.setSelectedTunerConfiguration(
// TunerType.AIRSPY_R820T, mController.getDeviceInfo().getSerialNumber(), config );
save();
}
catch ( /*UsbException |*/ SourceException e1 )
{
JOptionPane.showMessageDialog(
AirspyTunerConfigurationPanel.this,
"Airspy Tuner Controller - couldn't "
+ "apply the tuner configuration settings - " +
e1.getLocalizedMessage() );
mLog.error( "Airspy Tuner Controller - couldn't apply "
+ "config [" + config.getName() + "]", e1 );
}
}
/**
* Constructs a combo box model for the tuner configuration combo component
* by assembling a list of the tuner configurations appropriate for this
* specific tuner
*/
private ComboBoxModel<AirspyTunerConfiguration> getModel()
{
// ArrayList<TunerConfiguration> configs =
// mSettingsManager.getTunerConfigurations( TunerType.AIRSPY_R820T );
DefaultComboBoxModel<AirspyTunerConfiguration> model =
new DefaultComboBoxModel<AirspyTunerConfiguration>();
// for( TunerConfiguration config: configs )
// {
// model.addElement( (AirspyTunerConfiguration)config );
// }
return model;
}
/**
* Retrieves a specific (named) tuner configuration
*/
private AirspyTunerConfiguration getNamedConfiguration( String name )
{
// ArrayList<TunerConfiguration> configs =
// mSettingsManager.getTunerConfigurations( TunerType.AIRSPY_R820T );
// for( TunerConfiguration config: configs )
// {
// if( config.getName().contentEquals( name ) )
// {
// return (AirspyTunerConfiguration)config;
// }
// }
return null;
}
/**
* Saves current tuner configuration settings
*/
private void save()
{
// mSettingsManager.save();
}
}

View File

@@ -0,0 +1,720 @@
/*******************************************************************************
* SDR Trunk
* Copyright (C) 2015-2016 Dennis Sheirer
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>
******************************************************************************/
package source.tuner.airspy;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.FocusEvent;
import java.awt.event.FocusListener;
import java.text.DecimalFormat;
import java.util.List;
import javax.swing.DefaultComboBoxModel;
import javax.swing.JButton;
import javax.swing.JCheckBox;
import javax.swing.JComboBox;
import javax.swing.JLabel;
import javax.swing.JOptionPane;
import javax.swing.JSeparator;
import javax.swing.JSlider;
import javax.swing.JSpinner;
import javax.swing.JTextField;
import javax.swing.SpinnerModel;
import javax.swing.SpinnerNumberModel;
import javax.swing.SwingConstants;
import javax.swing.event.ChangeEvent;
import javax.swing.event.ChangeListener;
import javax.usb.UsbException;
import net.miginfocom.swing.MigLayout;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.usb4java.LibUsbException;
import source.SourceException;
import source.tuner.airspy.AirspyTunerController.Gain;
import source.tuner.airspy.AirspyTunerController.GainMode;
import source.tuner.configuration.TunerConfiguration;
import source.tuner.configuration.TunerConfigurationEditor;
import source.tuner.configuration.TunerConfigurationModel;
public class AirspyTunerEditor extends TunerConfigurationEditor
{
private static final long serialVersionUID = 1L;
private final static Logger mLog =
LoggerFactory.getLogger( AirspyTunerEditor.class );
private JTextField mConfigurationName;
private JButton mTunerInfo;
private JComboBox<AirspySampleRate> mSampleRateCombo;
private JSpinner mFrequencyCorrection;
private JComboBox<GainMode> mGainModeCombo;
private JSlider mMasterGain;
private JLabel mMasterGainValueLabel;
private JSlider mIFGain;
private JLabel mIFGainValueLabel;
private JSlider mLNAGain;
private JLabel mLNAGainValueLabel;
private JSlider mMixerGain;
private JLabel mMixerGainValueLabel;
private JCheckBox mLNAAGC;
private JCheckBox mMixerAGC;
private AirspyTunerController mController;
private boolean mLoading;
public AirspyTunerEditor( TunerConfigurationModel tunerConfigurationModel,
AirspyTuner tuner )
{
super( tunerConfigurationModel );
mController = tuner.getController();
init();
}
private AirspyTunerConfiguration getConfiguration()
{
if( hasItem() )
{
return (AirspyTunerConfiguration)getItem();
}
return null;
}
private void init()
{
setLayout( new MigLayout( "fill,wrap 4", "[right][grow,fill][right][grow,fill]",
"[][][][][][grow]" ) );
add( new JLabel( "Airspy Tuner Configuration" ), "span,align center" );
// tabs.add( "Info", new AirspyInformationPanel( mController ) );
mConfigurationName = new JTextField();
mConfigurationName.setEnabled( false );
mConfigurationName.addFocusListener( new FocusListener()
{
@Override
public void focusLost( FocusEvent e )
{
save();
}
@Override
public void focusGained( FocusEvent e ) {}
} );
add( new JLabel( "Name:" ) );
add( mConfigurationName, "span 2" );
mTunerInfo = new JButton( "Tuner Info" );
mTunerInfo.setEnabled( false );
mTunerInfo.addActionListener( new ActionListener()
{
@Override
public void actionPerformed( ActionEvent e )
{
JOptionPane.showMessageDialog( AirspyTunerEditor.this, getTunerInfo(),
"Tuner Info", JOptionPane.INFORMATION_MESSAGE );
}
} );
add( mTunerInfo );
/**
* Sample Rate
*/
add( new JLabel( "Sample Rate:" ) );
List<AirspySampleRate> rates = mController.getSampleRates();
mSampleRateCombo = new JComboBox<AirspySampleRate>(
new DefaultComboBoxModel<AirspySampleRate>( rates.toArray(
new AirspySampleRate[ rates.size() ] ) ) );
mSampleRateCombo.setEnabled( false );
mSampleRateCombo.addActionListener( new ActionListener()
{
@Override
public void actionPerformed( ActionEvent e )
{
AirspySampleRate rate = (AirspySampleRate)mSampleRateCombo.getSelectedItem();
try
{
mController.setSampleRate( rate );
save();
}
catch ( LibUsbException | UsbException e1 )
{
JOptionPane.showMessageDialog( AirspyTunerEditor.this,
"Couldn't set sample rate to " + rate.getLabel() );
mLog.error( "Error setting airspy sample rate", e1 );
}
}
} );
add( mSampleRateCombo );
/**
* Frequency Correction
*/
SpinnerModel model =
new SpinnerNumberModel( 0.0, //initial value
-1000.0, //min
1000.0, //max
0.1 ); //step
mFrequencyCorrection = new JSpinner( model );
mFrequencyCorrection.setEnabled( false );
JSpinner.NumberEditor editor =
(JSpinner.NumberEditor)mFrequencyCorrection.getEditor();
DecimalFormat format = editor.getFormat();
format.setMinimumFractionDigits( 1 );
editor.getTextField().setHorizontalAlignment( SwingConstants.CENTER );
mFrequencyCorrection.addChangeListener( new ChangeListener()
{
@Override
public void stateChanged( ChangeEvent e )
{
final double value = ((SpinnerNumberModel)mFrequencyCorrection
.getModel()).getNumber().doubleValue();
try
{
mController.setFrequencyCorrection( value );
}
catch ( SourceException e1 )
{
mLog.error( "Error setting frequency correction value", e1 );
}
save();
}
} );
add( new JLabel( "PPM:" ) );
add( mFrequencyCorrection );
add( new JSeparator(), "span,growx,push" );
/**
* Gain Mode
*/
add( new JLabel( "Gain Mode:" ) );
mGainModeCombo = new JComboBox<AirspyTunerController.GainMode>( GainMode.values() );
mGainModeCombo.setEnabled( false );
mGainModeCombo.addActionListener( new ActionListener()
{
@Override
public void actionPerformed( ActionEvent e )
{
GainMode mode = (GainMode)mGainModeCombo.getSelectedItem();
updateGainComponents( mode );
if( hasItem() )
{
AirspyTunerConfiguration airspy = getConfiguration();
Gain gain = airspy.getGain();
if( mode == GainMode.CUSTOM )
{
mIFGain.setValue( airspy.getIFGain() );
mMixerGain.setValue( airspy.getMixerGain() );
mMixerAGC.setSelected( airspy.isMixerAGC() );
mLNAGain.setValue( airspy.getLNAGain() );
mLNAAGC.setSelected( airspy.isLNAAGC() );
}
else
{
mMixerAGC.setSelected( false );
mLNAAGC.setSelected( false );
mMasterGain.setValue( gain.getValue() );
mIFGain.setValue( gain.getIF() );
mMixerGain.setValue( gain.getMixer() );
mLNAGain.setValue( gain.getLNA() );
}
}
save();
}
} );
add( mGainModeCombo, "wrap" );
/**
* Gain
*/
add( new JLabel( "Master:" ) );
mMasterGain = new JSlider( JSlider.HORIZONTAL,
AirspyTunerController.GAIN_MIN,
AirspyTunerController.GAIN_MAX,
AirspyTunerController.GAIN_MIN );
mMasterGain.setMajorTickSpacing( 1 );
mMasterGain.setPaintTicks( true );
mMasterGain.addChangeListener( new ChangeListener()
{
@Override
public void stateChanged( ChangeEvent event )
{
GainMode mode = (GainMode)mGainModeCombo.getSelectedItem();
int value = mMasterGain.getValue();
Gain gain = Gain.getGain( mode, value );
try
{
mController.setGain( gain );
save();
mMasterGainValueLabel.setText( String.valueOf( gain.getValue() ) );
}
catch ( Exception e )
{
mLog.error( "Couldn't set airspy gain to:" + gain.name(), e );
JOptionPane.showMessageDialog( mMasterGain, "Couldn't set gain value to " +
gain.getValue() );
}
}
} );
add( mMasterGain, "span 2" );
mMasterGainValueLabel = new JLabel( "0" );
add( mMasterGainValueLabel );
add( new JLabel( "IF:" ) );
mIFGain = new JSlider( JSlider.HORIZONTAL,
AirspyTunerController.IF_GAIN_MIN,
AirspyTunerController.IF_GAIN_MAX,
AirspyTunerController.IF_GAIN_MIN );
mIFGain.setMajorTickSpacing( 1 );
mIFGain.setPaintTicks( true );
mIFGain.addChangeListener( new ChangeListener()
{
@Override
public void stateChanged( ChangeEvent event )
{
int gain = mIFGain.getValue();
try
{
mController.setIFGain( gain );
save();
mIFGainValueLabel.setText( String.valueOf( gain ) );
}
catch ( Exception e )
{
mLog.error( "Couldn't set airspy IF gain to:" + gain, e );
JOptionPane.showMessageDialog( mIFGain, "Couldn't set IF gain value to " + gain );
}
}
} );
add( mIFGain, "span 2" );
mIFGainValueLabel = new JLabel( "0" );
add( mIFGainValueLabel );
/**
* Mixer Gain
*/
add( new JLabel( "Mixer:" ) );
mMixerGain = new JSlider( JSlider.HORIZONTAL,
AirspyTunerController.MIXER_GAIN_MIN,
AirspyTunerController.MIXER_GAIN_MAX,
AirspyTunerController.MIXER_GAIN_MIN );
mMixerGain.setMajorTickSpacing( 1 );
mMixerGain.setPaintTicks( true );
mMixerGain.addChangeListener( new ChangeListener()
{
@Override
public void stateChanged( ChangeEvent event )
{
int gain = mMixerGain.getValue();
try
{
mController.setMixerGain( gain );
save();
mMixerGainValueLabel.setText( String.valueOf( gain ) );
}
catch ( Exception e )
{
mLog.error( "Couldn't set airspy Mixer gain to:" + gain, e );
JOptionPane.showMessageDialog( mIFGain, "Couldn't set Mixer gain value to " + gain );
}
}
} );
add( mMixerGain, "span 2" );
mMixerGainValueLabel = new JLabel( "0" );
add( mMixerGainValueLabel );
add( new JLabel( "LNA:" ) );
mLNAGain = new JSlider( JSlider.HORIZONTAL,
AirspyTunerController.LNA_GAIN_MIN,
AirspyTunerController.LNA_GAIN_MAX,
AirspyTunerController.LNA_GAIN_MIN );
mLNAGain.setMajorTickSpacing( 1 );
mLNAGain.setPaintTicks( true );
mLNAGain.addChangeListener( new ChangeListener()
{
@Override
public void stateChanged( ChangeEvent event )
{
int gain = mLNAGain.getValue();
try
{
mController.setLNAGain( gain );
save();
mLNAGainValueLabel.setText( String.valueOf( gain ) );
}
catch ( Exception e )
{
mLog.error( "Couldn't set airspy LNA gain to:" + gain, e );
JOptionPane.showMessageDialog( mIFGain, "Couldn't set LNA gain value to " + gain );
}
}
} );
add( mLNAGain, "span 2" );
mLNAGainValueLabel = new JLabel( "0" );
add( mLNAGainValueLabel );
mMixerAGC = new JCheckBox( "Mixer AGC" );
mMixerAGC.addActionListener( new ActionListener()
{
@Override
public void actionPerformed( ActionEvent e )
{
try
{
mController.setMixerAGC( mMixerAGC.isSelected() );
save();
}
catch ( Exception e1 )
{
mLog.error( "Error setting Mixer AGC Enabled" );
}
}
} );
add( mMixerAGC, "span 2,center" );
mLNAAGC = new JCheckBox( "LNA AGC" );
mLNAAGC.addActionListener( new ActionListener()
{
@Override
public void actionPerformed( ActionEvent e )
{
try
{
mController.setLNAAGC( mLNAAGC.isSelected() );
save();
}
catch ( Exception e1 )
{
mLog.error( "Error setting LNA AGC Enabled" );
}
}
} );
add( mLNAAGC, "span 2,center" );
}
/**
* Updates the enabled state of each of the gain controls according to the
* specified gain mode. The master gain control is enabled for linearity
* and sensitivity and the individual gain controls are disabled, and
* vice-versa for custom mode.
*/
private void updateGainComponents( GainMode mode )
{
switch( mode )
{
case LINEARITY:
if( !mMasterGain.isEnabled() )
{
mMasterGain.setEnabled( true );
mMasterGainValueLabel.setEnabled( true );
}
if( mIFGain.isEnabled() )
{
mIFGain.setEnabled( false );
mIFGainValueLabel.setEnabled( false );
}
if( mLNAGain.isEnabled() )
{
mLNAAGC.setEnabled( false );
mLNAGainValueLabel.setEnabled( false );
mLNAGain.setEnabled( false );
}
if( mMixerGain.isEnabled() )
{
mMixerGainValueLabel.setEnabled( false );
mMixerAGC.setEnabled( false );
mMixerGain.setEnabled( false );
}
break;
case SENSITIVITY:
if( !mMasterGain.isEnabled() )
{
mMasterGain.setEnabled( true );
mMasterGainValueLabel.setEnabled( true );
}
if( mIFGain.isEnabled() )
{
mIFGain.setEnabled( false );
mIFGainValueLabel.setEnabled( false );
}
if( mLNAGain.isEnabled() )
{
mLNAAGC.setEnabled( false );
mLNAGainValueLabel.setEnabled( false );
mLNAGain.setEnabled( false );
}
if( mMixerGain.isEnabled() )
{
mMixerGainValueLabel.setEnabled( false );
mMixerAGC.setEnabled( false );
mMixerGain.setEnabled( false );
}
break;
case CUSTOM:
if( mMasterGain.isEnabled() )
{
mMasterGain.setEnabled( false );
mMasterGainValueLabel.setEnabled( false );
}
if( !mIFGain.isEnabled() )
{
mIFGain.setEnabled( true );
mIFGainValueLabel.setEnabled( true );
}
if( !mLNAGain.isEnabled() )
{
mLNAAGC.setEnabled( true );
mLNAGainValueLabel.setEnabled( true );
mLNAGain.setEnabled( true );
}
if( !mMixerGain.isEnabled() )
{
mMixerGainValueLabel.setEnabled( true );
mMixerAGC.setEnabled( true );
mMixerGain.setEnabled( true );
}
default:
break;
}
}
@Override
public void save()
{
if( hasItem() && !mLoading )
{
AirspyTunerConfiguration config = getConfiguration();
config.setName( mConfigurationName.getText() );
config.setSampleRate( ((AirspySampleRate)mSampleRateCombo.getSelectedItem()).getRate() );
double value = ((SpinnerNumberModel)mFrequencyCorrection.getModel()).getNumber().doubleValue();
config.setFrequencyCorrection( value );
config.setGain( Gain.getGain( (GainMode)mGainModeCombo.getSelectedItem(), mMasterGain.getValue() ) );
config.setIFGain( mIFGain.getValue() );
config.setMixerGain( mMixerGain.getValue() );
config.setLNAGain( mLNAGain.getValue() );
config.setMixerAGC( mMixerAGC.isSelected() );
config.setLNAAGC( mLNAAGC.isSelected() );
}
}
private AirspySampleRate fromValue( int value )
{
List<AirspySampleRate> rates = mController.getSampleRates();
for( AirspySampleRate rate: rates )
{
if( rate.getRate() == value )
{
return rate;
}
}
if( rates.size() > 0 )
{
return rates.get( 0 );
}
return null;
}
/**
* Sets all controls to the argument enabled state
*/
private void setControlsEnabled( boolean enabled )
{
if( mConfigurationName.isEnabled() != enabled )
{
mConfigurationName.setEnabled( enabled );
}
if( mTunerInfo.isEnabled() != enabled )
{
mTunerInfo.setEnabled( enabled );
}
if( mSampleRateCombo.isEnabled() != enabled )
{
mSampleRateCombo.setEnabled( enabled );
}
if( mFrequencyCorrection.isEnabled() != enabled )
{
mFrequencyCorrection.setEnabled( enabled );
}
if( mGainModeCombo.isEnabled() != enabled )
{
mGainModeCombo.setEnabled( enabled );
}
if( mMasterGain.isEnabled() != enabled )
{
mMasterGain.setEnabled( enabled );
}
if( mIFGain.isEnabled() != enabled )
{
mIFGain.setEnabled( enabled );
}
if( mMixerGain.isEnabled() != enabled )
{
mMixerGain.setEnabled( enabled );
}
if( mMixerAGC.isEnabled() != enabled )
{
mMixerAGC.setEnabled( enabled );
}
if( mLNAGain.isEnabled() != enabled )
{
mLNAGain.setEnabled( enabled );
}
if( mLNAAGC.isEnabled() != enabled )
{
mLNAAGC.setEnabled( enabled );
}
}
/**
* Applies the tuner configuration to the editor. If the configuration is assigned to the
* currently selected tuner, then the settings are applied.
*/
@Override
public void setItem( TunerConfiguration config )
{
super.setItem( config );
if( hasItem() && getItem().isAssigned() )
{
AirspyTunerConfiguration airspy = getConfiguration();
setControlsEnabled( true );
mConfigurationName.setText( airspy.getName() );
AirspySampleRate rate = fromValue( airspy.getSampleRate() );
if( rate != null )
{
mSampleRateCombo.setSelectedItem( rate );
}
mFrequencyCorrection.setValue( airspy.getFrequencyCorrection() );
GainMode mode = Gain.getGainMode( airspy.getGain() );
//This will set the master, IF, Mixer, LNA and AGC controls
mGainModeCombo.setSelectedItem( mode );
}
else
{
setControlsEnabled( false );
mConfigurationName.setText( hasItem() ? getItem().getName() : "" );
}
}
private String getTunerInfo()
{
StringBuilder sb = new StringBuilder();
AirspyDeviceInformation info = mController.getDeviceInfo();
sb.append( "<html><h3>Airspy Tuner</h3>" );
sb.append( "<b>Serial: </b>" );
sb.append( info.getSerialNumber() );
sb.append( "<br>" );
sb.append( "<b>Firmware: </b>" );
String[] firmware = info.getVersion().split( " " );
sb.append( firmware.length > 1 ? firmware[ 0 ] : info.getVersion() );
sb.append( "<br>" );
sb.append( "<b>Part: </b>" );
sb.append( info.getPartNumber() );
sb.append( "<br>" );
sb.append( "<b>Board ID: </b>" );
sb.append( info.getBoardID().getLabel() );
sb.append( "<br>" );
return sb.toString();
}
}

View File

@@ -1,112 +0,0 @@
/*******************************************************************************
* SDR Trunk
* Copyright (C) 2015 Dennis Sheirer
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>
******************************************************************************/
package source.tuner.airspy;
import gui.control.JFrequencyControl;
import java.awt.Color;
import javax.swing.JLabel;
import javax.swing.JPanel;
import net.miginfocom.swing.MigLayout;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import settings.SettingsManager;
import source.SourceException;
import source.tuner.frequency.FrequencyChangeEvent;
import source.tuner.frequency.FrequencyChangeEvent.Event;
import source.tuner.frequency.IFrequencyChangeProcessor;
import com.jidesoft.swing.JideTabbedPane;
public class AirspyTunerEditorPanel extends JPanel
implements IFrequencyChangeProcessor
{
private static final long serialVersionUID = 1L;
private final static Logger mLog =
LoggerFactory.getLogger( AirspyTunerEditorPanel.class );
private JFrequencyControl mFrequencyControl;
private AirspyTuner mTuner;
private AirspyTunerController mController;
private SettingsManager mSettingsManager;
public AirspyTunerEditorPanel( AirspyTuner tuner,
SettingsManager settingsManager )
{
mTuner = tuner;
mController = mTuner.getController();
mSettingsManager = settingsManager;
initGUI();
}
private void initGUI()
{
setLayout( new MigLayout( "fill,wrap 2",
"[right,grow][grow]",
"[][][][][][grow]" ) );
add( new JLabel( "Airspy Tuner" ), "span,align center" );
mFrequencyControl = new JFrequencyControl();
mFrequencyControl.addListener( this );
/* Add frequency control as frequency change listener. This creates a
* feedback loop, so the control does not rebroadcast the event */
mTuner.getTunerController().addListener( mFrequencyControl );
mFrequencyControl.setFrequency( mController.getFrequency(), false );
add( mFrequencyControl, "span,align center" );
JideTabbedPane tabs = new JideTabbedPane();
tabs.setFont( this.getFont() );
tabs.setForeground( Color.BLACK );
add( tabs, "span,grow,push" );
tabs.add( "Config", new AirspyTunerConfigurationPanel(
mSettingsManager, mTuner.getController() ) );
tabs.add( "Info", new AirspyInformationPanel( mTuner.getController() ) );
}
@Override
public void frequencyChanged( FrequencyChangeEvent event )
{
if( event.getEvent() == Event.NOTIFICATION_FREQUENCY_CHANGE )
{
try
{
mController.setFrequency( event.getValue().longValue() );
}
catch ( SourceException e )
{
mLog.error( "error setting frequency [" +
event.getValue().longValue() + "]", e );
}
}
}
}

View File

@@ -1,7 +1,6 @@
package source.tuner.configuration;
import gui.editor.Editor;
import source.tuner.TunerType;
public abstract class TunerConfigurationEditor extends Editor<TunerConfiguration>
{
@@ -14,8 +13,6 @@ public abstract class TunerConfigurationEditor extends Editor<TunerConfiguration
mTunerConfigurationModel = model;
}
public abstract boolean canEdit( TunerType tunerType );
public TunerConfigurationModel getTunerConfigurationModel()
{
return mTunerConfigurationModel;

View File

@@ -4,7 +4,9 @@ import gui.editor.Editor;
import gui.editor.EmptyEditor;
import source.tuner.Tuner;
import source.tuner.TunerType;
import source.tuner.airspy.AirspyTuner;
import source.tuner.airspy.AirspyTunerConfiguration;
import source.tuner.airspy.AirspyTunerEditor;
import source.tuner.fcd.proV1.FCD1TunerConfiguration;
import source.tuner.fcd.proplusV2.FCD2TunerConfiguration;
import source.tuner.hackrf.HackRFTunerConfiguration;
@@ -45,7 +47,7 @@ public class TunerConfigurationFactory
switch( tuner.getTunerType() )
{
case AIRSPY_R820T:
break;
return new AirspyTunerEditor( model, (AirspyTuner)tuner );
case ELONICS_E4000:
break;
case FUNCUBE_DONGLE_PRO:

View File

@@ -23,6 +23,7 @@ import java.awt.event.FocusEvent;
import java.awt.event.FocusListener;
import java.text.DecimalFormat;
import javax.swing.JButton;
import javax.swing.JComboBox;
import javax.swing.JLabel;
import javax.swing.JOptionPane;
@@ -43,13 +44,15 @@ import org.slf4j.LoggerFactory;
import org.usb4java.LibUsbException;
import source.SourceException;
import source.tuner.TunerType;
import source.tuner.airspy.AirspyDeviceInformation;
import source.tuner.airspy.AirspyTunerEditor;
import source.tuner.configuration.TunerConfiguration;
import source.tuner.configuration.TunerConfigurationEditor;
import source.tuner.configuration.TunerConfigurationEvent;
import source.tuner.configuration.TunerConfigurationEvent.Event;
import source.tuner.configuration.TunerConfigurationModel;
import source.tuner.rtl.RTL2832Tuner;
import source.tuner.rtl.RTL2832TunerController.Descriptor;
import source.tuner.rtl.RTL2832TunerController.SampleRate;
import source.tuner.rtl.r820t.R820TTunerController.R820TGain;
import source.tuner.rtl.r820t.R820TTunerController.R820TLNAGain;
@@ -67,6 +70,7 @@ public class R820TTunerEditor extends TunerConfigurationEditor
private R820TTunerController mController;
private JTextField mConfigurationName;
private JButton mTunerInfo;
private JSpinner mFrequencyCorrection;
private JComboBox<R820TGain> mComboMasterGain;
private JComboBox<R820TMixerGain> mComboMixerGain;
@@ -84,12 +88,6 @@ public class R820TTunerEditor extends TunerConfigurationEditor
init();
}
@Override
public boolean canEdit( TunerType tunerType )
{
return tunerType == TunerType.RAFAELMICRO_R820T;
}
@Override
public void save()
{
@@ -169,6 +167,11 @@ public class R820TTunerEditor extends TunerConfigurationEditor
mConfigurationName.setEnabled( enabled );
}
if( mTunerInfo.isEnabled() != enabled )
{
mTunerInfo.setEnabled( enabled );
}
if( mFrequencyCorrection.isEnabled() != enabled )
{
mFrequencyCorrection.setEnabled( enabled );
@@ -213,9 +216,9 @@ public class R820TTunerEditor extends TunerConfigurationEditor
private void init()
{
setLayout( new MigLayout( "fill,wrap 4", "[right][grow,fill][right][grow,fill]",
"[][][][][][][grow]" ) );
"[][][][][][][][grow]" ) );
add( new JLabel( "R820T Tuner Configuration" ), "span, align center" );
add( new JLabel( "R820T Tuner Configuration" ), "span,align center" );
/**
* Tuner Configuration Name
@@ -234,7 +237,21 @@ public class R820TTunerEditor extends TunerConfigurationEditor
} );
add( new JLabel( "Name:" ) );
add( mConfigurationName, "span,grow" );
add( mConfigurationName, "span 2" );
mTunerInfo = new JButton( "Tuner Info" );
mTunerInfo.setEnabled( false );
mTunerInfo.addActionListener( new ActionListener()
{
@Override
public void actionPerformed( ActionEvent e )
{
JOptionPane.showMessageDialog( R820TTunerEditor.this, getTunerInfo(),
"Tuner Info", JOptionPane.INFORMATION_MESSAGE );
}
} );
add( mTunerInfo );
mComboSampleRate = new JComboBox<>( SampleRate.values() );
mComboSampleRate.setEnabled( false );
@@ -312,10 +329,12 @@ public class R820TTunerEditor extends TunerConfigurationEditor
add( mFrequencyCorrection );
add( new JSeparator( JSeparator.HORIZONTAL ), "span,grow" );
/**
* Gain Controls
*/
add( new JLabel( "Gain" ), "span" );
/* Master Gain Control */
mComboMasterGain = new JComboBox<R820TGain>( R820TGain.values() );
mComboMasterGain.setEnabled( false );
@@ -500,4 +519,48 @@ public class R820TTunerEditor extends TunerConfigurationEditor
add( new JLabel( "VGA:" ) );
add( mComboVGAGain );
}
private String getTunerInfo()
{
StringBuilder sb = new StringBuilder();
Descriptor descriptor = mController.getDescriptor();
sb.append( "<html><h3>RTL-2832 with R820T Tuner</h3>" );
if( descriptor == null )
{
sb.append( "No EEPROM Descriptor Available" );
}
else
{
sb.append( "<b>USB ID: </b>" );
sb.append( descriptor.getVendorID() );
sb.append( ":" );
sb.append( descriptor.getProductID() );
sb.append( "<br>" );
sb.append( "<b>Vendor: </b>" );
sb.append( descriptor.getVendorLabel() );
sb.append( "<br>" );
sb.append( "<b>Product: </b>" );
sb.append( descriptor.getProductLabel() );
sb.append( "<br>" );
sb.append( "<b>Serial: </b>" );
sb.append( descriptor.getSerial() );
sb.append( "<br>" );
sb.append( "<b>IR Enabled: </b>" );
sb.append( descriptor.irEnabled() );
sb.append( "<br>" );
sb.append( "<b>Remote Wake: </b>" );
sb.append( descriptor.remoteWakeupEnabled() );
sb.append( "<br>" );
}
return sb.toString();
}
}