mirror of
https://github.com/DSheirer/sdrtrunk.git
synced 2026-11-13 17:17:29 -05:00
Updates pull request from Roman Tsypuk to convert the build system from
ant to gradle. Removes linux and windows application launch scripts and produces an executable jar with all resources included.
This commit is contained in:
@@ -0,0 +1,157 @@
|
||||
package io.github.dsheirer.source.tuner.airspy;
|
||||
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
import java.util.Arrays;
|
||||
|
||||
public class AirspyDeviceInformation
|
||||
{
|
||||
private final static Logger mLog =
|
||||
LoggerFactory.getLogger( AirspyDeviceInformation.class );
|
||||
|
||||
private AirspyTunerController.BoardID mBoardID = AirspyTunerController.BoardID.UNKNOWN;
|
||||
private String mFirmwareVersion = "Unknown";
|
||||
private String mPartNumber = "Unknown";
|
||||
private String mSerialNumber = "Unknown";
|
||||
|
||||
/**
|
||||
* Airspy Device Information - provides parsing and access to device
|
||||
* information components.
|
||||
*/
|
||||
public AirspyDeviceInformation()
|
||||
{
|
||||
}
|
||||
|
||||
public void setBoardID( int boardID )
|
||||
{
|
||||
mBoardID = AirspyTunerController.BoardID.fromValue( boardID );
|
||||
}
|
||||
|
||||
public AirspyTunerController.BoardID getBoardID()
|
||||
{
|
||||
return mBoardID;
|
||||
}
|
||||
|
||||
public void setVersion( byte[] data )
|
||||
{
|
||||
if( data != null && data.length > 0 )
|
||||
{
|
||||
/* Truncate the version string if we have a line break - ASCII 10 */
|
||||
for( int x = 0; x < data.length; x++ )
|
||||
{
|
||||
if( data[ x ] == (byte)10 )
|
||||
{
|
||||
mFirmwareVersion = new String( Arrays.copyOf( data, x ) );
|
||||
mFirmwareVersion = mFirmwareVersion.replace( "AirSpy NOS ", "" );
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
mFirmwareVersion = new String( data );
|
||||
mFirmwareVersion = mFirmwareVersion.replace( "AirSpy NOS ", "" );
|
||||
}
|
||||
else
|
||||
{
|
||||
mLog.error( "Error setting airspy version byte data - null:" +
|
||||
( data == null ? " TRUE" : " FALSE length:" + data.length ) );
|
||||
}
|
||||
}
|
||||
|
||||
public String getVersion()
|
||||
{
|
||||
return mFirmwareVersion;
|
||||
}
|
||||
|
||||
public void setPartAndSerialNumber( byte[] data )
|
||||
{
|
||||
if( data != null && data.length == 24 )
|
||||
{
|
||||
//Note: values are byte-reversed (big-endian) 32-bit chunks
|
||||
StringBuilder part = new StringBuilder();
|
||||
|
||||
part.append( format( data[ 3 ] ) );
|
||||
part.append( format( data[ 2 ] ) );
|
||||
part.append( format( data[ 1 ] ) );
|
||||
part.append( format( data[ 0 ] ) );
|
||||
part.append( format( data[ 7 ] ) );
|
||||
part.append( format( data[ 6 ] ) );
|
||||
part.append( format( data[ 5 ] ) );
|
||||
part.append( format( data[ 4 ] ) );
|
||||
|
||||
mPartNumber = part.toString();
|
||||
|
||||
StringBuilder serial = new StringBuilder();
|
||||
|
||||
//Note: current airspy library only exposes 64-bits of serial number
|
||||
//address space, but appears to have room for 128-bits. We won't
|
||||
//add the first 64 bits if it's zeros
|
||||
if( !( data[ 8 ] == 0 && data[ 9 ] == 0 && data[ 10 ] == 0 && data[ 11 ] == 0 ) )
|
||||
{
|
||||
serial.append( format( data[ 11 ] ) );
|
||||
serial.append( format( data[ 10 ] ) );
|
||||
serial.append( format( data[ 9 ] ) );
|
||||
serial.append( format( data[ 8 ] ) );
|
||||
serial.append( "-" );
|
||||
}
|
||||
|
||||
if( !( data[ 12 ] == 0 && data[ 13 ] == 0 && data[ 14 ] == 0 && data[ 15 ] == 0 ) )
|
||||
{
|
||||
serial.append( format( data[ 15 ] ) );
|
||||
serial.append( format( data[ 14 ] ) );
|
||||
serial.append( format( data[ 13 ] ) );
|
||||
serial.append( format( data[ 12 ] ) );
|
||||
serial.append( "-" );
|
||||
}
|
||||
|
||||
serial.append( format( data[ 19 ] ) );
|
||||
serial.append( format( data[ 18 ] ) );
|
||||
serial.append( format( data[ 17 ] ) );
|
||||
serial.append( format( data[ 16 ] ) );
|
||||
serial.append( "-" );
|
||||
serial.append( format( data[ 23 ] ) );
|
||||
serial.append( format( data[ 22 ] ) );
|
||||
serial.append( format( data[ 21 ] ) );
|
||||
serial.append( format( data[ 20 ] ) );
|
||||
|
||||
mSerialNumber = serial.toString();
|
||||
}
|
||||
else
|
||||
{
|
||||
mLog.error( "Error setting airspy part and serial byte data - null:" +
|
||||
( data == null ? " TRUE" : " FALSE length:" + data.length ) );
|
||||
}
|
||||
}
|
||||
|
||||
private String format( byte value )
|
||||
{
|
||||
return String.format( "%02X", value );
|
||||
}
|
||||
|
||||
public String getSerialNumber()
|
||||
{
|
||||
return mSerialNumber;
|
||||
}
|
||||
|
||||
public String getPartNumber()
|
||||
{
|
||||
return mPartNumber;
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
StringBuilder sb = new StringBuilder();
|
||||
|
||||
sb.append( "Airspy Device Information\n" );
|
||||
sb.append( "Board: " );
|
||||
sb.append( getBoardID().getLabel() );
|
||||
sb.append( "\nPart Number: " );
|
||||
sb.append( getPartNumber() );
|
||||
sb.append( "\nSerial Number: " );
|
||||
sb.append( getSerialNumber() );
|
||||
sb.append( "\nFirmware: " );
|
||||
sb.append( getVersion() );
|
||||
|
||||
return sb.toString();
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,155 @@
|
||||
/*******************************************************************************
|
||||
* sdrtrunk
|
||||
* Copyright (C) 2014-2017 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 io.github.dsheirer.source.tuner.airspy;
|
||||
|
||||
import io.github.dsheirer.sample.adapter.ISampleAdapter;
|
||||
import io.github.dsheirer.dsp.filter.dc.DCRemovalFilter_RB;
|
||||
import io.github.dsheirer.dsp.filter.hilbert.HilbertTransform;
|
||||
|
||||
public class AirspySampleAdapter implements ISampleAdapter
|
||||
{
|
||||
private static final float SCALE_SIGNED_12_BIT_TO_FLOAT = 1.0f / 2048.0f;
|
||||
|
||||
private DCRemovalFilter_RB mDCFilter = new DCRemovalFilter_RB(0.01f);
|
||||
private HilbertTransform mHilbertTransform = new HilbertTransform();
|
||||
private boolean mSamplePacking = false;
|
||||
|
||||
|
||||
/**
|
||||
* Adapter to translate byte buffers received from the airspy tuner into
|
||||
* float buffers for processing.
|
||||
*/
|
||||
public AirspySampleAdapter()
|
||||
{
|
||||
}
|
||||
|
||||
/**
|
||||
* Sample packing places two 12-bit samples into 3 bytes when enabled or
|
||||
* places two 12-bit samples into 4 bytes when disabled.
|
||||
*
|
||||
* @param enabled
|
||||
*/
|
||||
public void setSamplePacking(boolean enabled)
|
||||
{
|
||||
mSamplePacking = enabled;
|
||||
}
|
||||
|
||||
@Override
|
||||
public float[] convert(byte[] samples)
|
||||
{
|
||||
float[] realSamples;
|
||||
|
||||
if(mSamplePacking)
|
||||
{
|
||||
realSamples = convertPacked(samples);
|
||||
}
|
||||
else
|
||||
{
|
||||
realSamples = convertUnpacked(samples);
|
||||
}
|
||||
|
||||
mDCFilter.filter(realSamples);
|
||||
|
||||
return mHilbertTransform.filter(realSamples);
|
||||
}
|
||||
|
||||
/**
|
||||
* Converts the byte array containing unsigned 12-bit short values into
|
||||
* signed float values in the range -1 to 1;
|
||||
*
|
||||
* @param data - byte array of unsigned 16-bit values
|
||||
* @return converted float values
|
||||
*/
|
||||
private float[] convertUnpacked(byte[] data)
|
||||
{
|
||||
float[] samples = new float[data.length / 2];
|
||||
|
||||
int pointer = 0;
|
||||
|
||||
for(int x = 0; x < data.length; x += 2)
|
||||
{
|
||||
samples[pointer++] = scale((data[x] & 0xFF) |
|
||||
(data[x + 1] << 8));
|
||||
}
|
||||
|
||||
return samples;
|
||||
}
|
||||
|
||||
/**
|
||||
* Converts every 3 bytes containing a pair of 12-bit unsigned values into
|
||||
* a pair of float values in the range -1 to 1;
|
||||
*
|
||||
* @param data1 - byte array of unsigned 12-bit values
|
||||
* @return converted float values
|
||||
*/
|
||||
private float[] convertPacked(byte[] data1)
|
||||
{
|
||||
byte[] data = new byte[data1.length];
|
||||
|
||||
//Convert big-endian to little-endian
|
||||
for(int x = 0; x < data1.length; x += 4)
|
||||
{
|
||||
data[x] = data1[x + 3];
|
||||
data[x + 1] = data1[x + 2];
|
||||
data[x + 2] = data1[x + 1];
|
||||
data[x + 3] = data1[x];
|
||||
}
|
||||
|
||||
int count = (int) ((float) data.length / 1.5f);
|
||||
|
||||
/* Ensure we have an even number of samples */
|
||||
if(count % 2 == 1)
|
||||
{
|
||||
count--;
|
||||
}
|
||||
|
||||
int bytes = (int) ((float) count * 1.5f);
|
||||
|
||||
float[] samples = new float[count];
|
||||
|
||||
int pointer = 0;
|
||||
|
||||
int first;
|
||||
int second;
|
||||
|
||||
for(int x = 0; x < bytes; x += 3)
|
||||
{
|
||||
first = ((data[x] << 4) & 0xFF0) |
|
||||
((data[x + 1] >> 4) & 0xF);
|
||||
|
||||
samples[pointer++] = scale(first);
|
||||
|
||||
second = ((data[x + 1] << 8) & 0xF00) |
|
||||
(data[x + 2] & 0xFF);
|
||||
|
||||
samples[pointer++] = scale(second);
|
||||
}
|
||||
|
||||
return samples;
|
||||
}
|
||||
|
||||
/**
|
||||
* Converts unsigned 12-bit values to signed 12-bit values and then scales
|
||||
* the signed value to a signed float value in range: -1.0 : +1.0
|
||||
*/
|
||||
public static float scale(int value)
|
||||
{
|
||||
return (float) ((value & 0xFFF) - 2048) * SCALE_SIGNED_12_BIT_TO_FLOAT;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,35 @@
|
||||
package io.github.dsheirer.source.tuner.airspy;
|
||||
|
||||
public class AirspySampleRate
|
||||
{
|
||||
private int mIndex;
|
||||
private int mValue;
|
||||
private String mLabel;
|
||||
|
||||
public AirspySampleRate( int index, int value, String label )
|
||||
{
|
||||
mIndex = index;
|
||||
mValue = value;
|
||||
mLabel = label;
|
||||
}
|
||||
|
||||
public int getIndex()
|
||||
{
|
||||
return mIndex;
|
||||
}
|
||||
|
||||
public int getRate()
|
||||
{
|
||||
return mValue;
|
||||
}
|
||||
|
||||
public String getLabel()
|
||||
{
|
||||
return mLabel;
|
||||
}
|
||||
|
||||
public String toString()
|
||||
{
|
||||
return getLabel();
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,127 @@
|
||||
/*******************************************************************************
|
||||
* 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 io.github.dsheirer.source.tuner.airspy;
|
||||
|
||||
import io.github.dsheirer.sample.Listener;
|
||||
import io.github.dsheirer.sample.complex.ComplexBuffer;
|
||||
import io.github.dsheirer.source.SourceException;
|
||||
import io.github.dsheirer.source.tuner.Tuner;
|
||||
import io.github.dsheirer.source.tuner.TunerChannel;
|
||||
import io.github.dsheirer.source.tuner.TunerChannelSource;
|
||||
import io.github.dsheirer.source.tuner.TunerClass;
|
||||
import io.github.dsheirer.source.tuner.TunerEvent;
|
||||
import io.github.dsheirer.source.tuner.TunerType;
|
||||
import io.github.dsheirer.source.tuner.airspy.AirspyTunerController.BoardID;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
import java.util.concurrent.RejectedExecutionException;
|
||||
|
||||
public class AirspyTuner extends Tuner
|
||||
{
|
||||
private final static Logger mLog = LoggerFactory.getLogger( AirspyTuner.class );
|
||||
|
||||
public AirspyTuner( AirspyTunerController controller )
|
||||
{
|
||||
super( "Airspy " + controller.getDeviceInfo().getSerialNumber(), controller );
|
||||
}
|
||||
|
||||
public AirspyTunerController getController()
|
||||
{
|
||||
return (AirspyTunerController)getTunerController();
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getUniqueID()
|
||||
{
|
||||
try
|
||||
{
|
||||
return getController().getDeviceInfo().getSerialNumber();
|
||||
}
|
||||
catch( Exception e )
|
||||
{
|
||||
mLog.error( "error getting serial number", e );
|
||||
}
|
||||
|
||||
return BoardID.AIRSPY.getLabel();
|
||||
}
|
||||
|
||||
@Override
|
||||
public TunerClass getTunerClass()
|
||||
{
|
||||
return TunerClass.AIRSPY;
|
||||
}
|
||||
|
||||
@Override
|
||||
public TunerType getTunerType()
|
||||
{
|
||||
return TunerType.AIRSPY_R820T;
|
||||
}
|
||||
|
||||
@Override
|
||||
public double getSampleSize()
|
||||
{
|
||||
return 13.0;
|
||||
}
|
||||
|
||||
@Override
|
||||
public TunerChannelSource getChannel( TunerChannel channel )
|
||||
throws RejectedExecutionException, SourceException
|
||||
{
|
||||
//TODO: this channel has a decimated sample rate of:
|
||||
// 10.0 MSps = 10,000,000 / 208 = 48076.923
|
||||
// 5.0 MSps = 5,000,000 / 104 = 48076.923
|
||||
// 2.5 MSps = 2,500,000 / 52 = 48076.923
|
||||
//Consider implementing a fractional resampler to get a correct 48 kHz
|
||||
//output sample rate
|
||||
|
||||
TunerChannelSource source = getController().getChannel( this, channel );
|
||||
|
||||
if( source != null )
|
||||
{
|
||||
broadcast( new TunerEvent( this, TunerEvent.Event.CHANNEL_COUNT ) );
|
||||
}
|
||||
|
||||
return source;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void releaseChannel( TunerChannelSource source )
|
||||
{
|
||||
/* Unregister for receiving samples */
|
||||
removeListener( (Listener<ComplexBuffer>)source );
|
||||
|
||||
/* Tell the controller to release the channel and cleanup */
|
||||
if( source != null )
|
||||
{
|
||||
getController().releaseChannel( source );
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void addListener( Listener<ComplexBuffer> listener )
|
||||
{
|
||||
getController().addListener( listener );
|
||||
}
|
||||
|
||||
@Override
|
||||
public void removeListener( Listener<ComplexBuffer> listener )
|
||||
{
|
||||
getController().removeListener( listener );
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,144 @@
|
||||
/*******************************************************************************
|
||||
* 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 io.github.dsheirer.source.tuner.airspy;
|
||||
|
||||
import io.github.dsheirer.source.tuner.TunerType;
|
||||
import io.github.dsheirer.source.tuner.airspy.AirspyTunerController.Gain;
|
||||
import io.github.dsheirer.source.tuner.configuration.TunerConfiguration;
|
||||
|
||||
import javax.xml.bind.annotation.XmlAttribute;
|
||||
|
||||
public class AirspyTunerConfiguration extends TunerConfiguration
|
||||
{
|
||||
private int mSampleRate = AirspyTunerController.DEFAULT_SAMPLE_RATE.getRate();
|
||||
private Gain mGain = AirspyTunerController.LINEARITY_GAIN_DEFAULT;
|
||||
private int mIFGain = AirspyTunerController.IF_GAIN_DEFAULT;
|
||||
private int mMixerGain = AirspyTunerController.MIXER_GAIN_DEFAULT;
|
||||
private int mLNAGain = AirspyTunerController.LNA_GAIN_DEFAULT;
|
||||
private double mFrequencyCorrection = 0.0d;
|
||||
|
||||
private boolean mMixerAGC = false;
|
||||
private boolean mLNAAGC = false;
|
||||
|
||||
/**
|
||||
* Default constructor for JAXB
|
||||
*/
|
||||
public AirspyTunerConfiguration()
|
||||
{
|
||||
}
|
||||
|
||||
public AirspyTunerConfiguration( String uniqueID, String name )
|
||||
{
|
||||
super( uniqueID, name );
|
||||
}
|
||||
|
||||
@Override
|
||||
public TunerType getTunerType()
|
||||
{
|
||||
return TunerType.AIRSPY_R820T;
|
||||
}
|
||||
|
||||
@XmlAttribute( name = "sample_rate" )
|
||||
public int getSampleRate()
|
||||
{
|
||||
return mSampleRate;
|
||||
}
|
||||
|
||||
public void setSampleRate( int sampleRate )
|
||||
{
|
||||
mSampleRate = sampleRate;
|
||||
}
|
||||
|
||||
@XmlAttribute( name = "gain" )
|
||||
public Gain getGain()
|
||||
{
|
||||
return mGain;
|
||||
}
|
||||
|
||||
public void setGain( Gain gain )
|
||||
{
|
||||
mGain = gain;
|
||||
}
|
||||
|
||||
@XmlAttribute( name = "if_gain" )
|
||||
public int getIFGain()
|
||||
{
|
||||
return mIFGain;
|
||||
}
|
||||
|
||||
public void setIFGain( int gain )
|
||||
{
|
||||
mIFGain = gain;
|
||||
}
|
||||
|
||||
@XmlAttribute( name = "mixer_gain" )
|
||||
public int getMixerGain()
|
||||
{
|
||||
return mMixerGain;
|
||||
}
|
||||
|
||||
public void setMixerGain( int gain )
|
||||
{
|
||||
mMixerGain = gain;
|
||||
}
|
||||
|
||||
@XmlAttribute( name = "lna_gain" )
|
||||
public int getLNAGain()
|
||||
{
|
||||
return mLNAGain;
|
||||
}
|
||||
|
||||
public void setLNAGain( int gain )
|
||||
{
|
||||
mLNAGain = gain;
|
||||
}
|
||||
|
||||
@XmlAttribute( name = "mixer_agc" )
|
||||
public boolean isMixerAGC()
|
||||
{
|
||||
return mMixerAGC;
|
||||
}
|
||||
|
||||
public void setMixerAGC( boolean enabled )
|
||||
{
|
||||
mMixerAGC = enabled;
|
||||
}
|
||||
|
||||
@XmlAttribute( name = "lna_agc" )
|
||||
public boolean isLNAAGC()
|
||||
{
|
||||
return mLNAAGC;
|
||||
}
|
||||
|
||||
public void setLNAAGC( boolean enabled )
|
||||
{
|
||||
mLNAAGC = enabled;
|
||||
}
|
||||
|
||||
@XmlAttribute( name = "frequency_correction" )
|
||||
public double getFrequencyCorrection()
|
||||
{
|
||||
return mFrequencyCorrection;
|
||||
}
|
||||
|
||||
public void setFrequencyCorrection( double value )
|
||||
{
|
||||
mFrequencyCorrection = value;
|
||||
}
|
||||
|
||||
}
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,754 @@
|
||||
/*******************************************************************************
|
||||
* 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 io.github.dsheirer.source.tuner.airspy;
|
||||
|
||||
import io.github.dsheirer.source.SourceException;
|
||||
import io.github.dsheirer.source.tuner.airspy.AirspyTunerController.Gain;
|
||||
import io.github.dsheirer.source.tuner.airspy.AirspyTunerController.GainMode;
|
||||
import io.github.dsheirer.source.tuner.configuration.TunerConfiguration;
|
||||
import io.github.dsheirer.source.tuner.configuration.TunerConfigurationEditor;
|
||||
import io.github.dsheirer.source.tuner.configuration.TunerConfigurationEvent;
|
||||
import io.github.dsheirer.source.tuner.configuration.TunerConfigurationModel;
|
||||
import net.miginfocom.swing.MigLayout;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
import org.usb4java.LibUsbException;
|
||||
|
||||
import javax.swing.*;
|
||||
import javax.swing.event.ChangeEvent;
|
||||
import javax.swing.event.ChangeListener;
|
||||
import javax.usb.UsbException;
|
||||
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;
|
||||
|
||||
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" );
|
||||
|
||||
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 | SourceException 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() );
|
||||
mMixerGain.setEnabled( !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() );
|
||||
mLNAGain.setEnabled( !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 );
|
||||
|
||||
Gain gain = Gain.getGain( (GainMode)mGainModeCombo.getSelectedItem(), mMasterGain.getValue() );
|
||||
|
||||
config.setGain( gain );
|
||||
config.setIFGain( mIFGain.getValue() );
|
||||
config.setMixerGain( mMixerGain.getValue() );
|
||||
config.setLNAGain( mLNAGain.getValue() );
|
||||
config.setMixerAGC( mMixerAGC.isSelected() );
|
||||
config.setLNAAGC( mLNAAGC.isSelected() );
|
||||
|
||||
getTunerConfigurationModel().broadcast( new TunerConfigurationEvent( config, TunerConfigurationEvent.Event.CHANGE ) );
|
||||
}
|
||||
}
|
||||
|
||||
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 );
|
||||
|
||||
mLoading = true;
|
||||
|
||||
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 );
|
||||
|
||||
if( mode == GainMode.CUSTOM )
|
||||
{
|
||||
mMasterGain.setValue( airspy.getGain().getValue() );
|
||||
mIFGain.setValue( airspy.getIFGain() );
|
||||
|
||||
if( airspy.isMixerAGC() )
|
||||
{
|
||||
mMixerAGC.setSelected( airspy.isMixerAGC() );
|
||||
mMixerGain.setEnabled( false );
|
||||
}
|
||||
else
|
||||
{
|
||||
mMixerGain.setValue( airspy.getMixerGain() );
|
||||
}
|
||||
|
||||
if( airspy.isLNAAGC() )
|
||||
{
|
||||
mLNAAGC.setSelected( airspy.isLNAAGC() );
|
||||
mLNAGain.setEnabled( false );
|
||||
}
|
||||
else
|
||||
{
|
||||
mLNAGain.setValue( airspy.getLNAGain() );
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
mMixerAGC.setSelected( false );
|
||||
mLNAAGC.setSelected( false );
|
||||
|
||||
Gain gain = airspy.getGain();
|
||||
|
||||
mMasterGain.setValue( gain.getValue() );
|
||||
mIFGain.setValue( gain.getIF() );
|
||||
mMixerGain.setValue( gain.getMixer() );
|
||||
mLNAGain.setValue( gain.getLNA() );
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
setControlsEnabled( false );
|
||||
mConfigurationName.setText( hasItem() ? getItem().getName() : "" );
|
||||
}
|
||||
|
||||
mLoading = false;
|
||||
}
|
||||
|
||||
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();
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user