Skip to content

Commit

Permalink
Merge pull request #1800 from srcejon/rttymod
Browse files Browse the repository at this point in the history
Add RTTY Modulator
  • Loading branch information
f4exb authored Sep 5, 2023
2 parents 7b85db4 + f2e167d commit 74977c8
Show file tree
Hide file tree
Showing 67 changed files with 8,113 additions and 90 deletions.
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -43,3 +43,4 @@ obj-x86_64-linux-gnu/*

/rescuesdriq/vendor/
/rescuesdriq/Godeps/
/.vs
1 change: 1 addition & 0 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -107,6 +107,7 @@ option(ENABLE_CHANNELTX_MODATV "Enable channeltx modatv plugin" ON)
option(ENABLE_CHANNELTX_MOD802.15.4 "Enable channeltx mod802.15.4 plugin" ON)
option(ENABLE_CHANNELTX_REMOTESOURCE "Enable channeltx remotesource plugin" ON)
option(ENABLE_CHANNELTX_FILESOURCE "Enable channeltx filesource plugin" ON)
option(ENABLE_CHANNELTX_MODRTTY "Enable channeltx modrtty plugin" ON)

# Channel MIMO enablers
option(ENABLE_CHANNELMIMO "Enable channelmimo plugins" ON)
Expand Down
Binary file added doc/img/RTTYMod_plugin.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
2 changes: 2 additions & 0 deletions plugins/channelrx/demoddsc/dscdemodsink.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -227,6 +227,8 @@ void DSCDemodSink::receiveBit(bool bit)
m_dscDecoder.init(m_phasingPatterns[i].m_offset);
m_gotSOP = true;
m_bitCount = 0;
m_rssiMagSqSum = 0.0;
m_rssiMagSqCount = 0;
break;
}
}
Expand Down
2 changes: 2 additions & 0 deletions plugins/channelrx/demodnavtex/navtexdemodsink.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -329,6 +329,8 @@ void NavtexDemodSink::receiveBit(bool bit)
m_gotSOP = true;
m_bitCount = 0;
m_sitorBDecoder.init();
m_rssiMagSqSum = 0.0;
m_rssiMagSqCount = 0;
}
else
{
Expand Down
8 changes: 7 additions & 1 deletion plugins/channelrx/demodrtty/readme.md
Original file line number Diff line number Diff line change
Expand Up @@ -79,7 +79,12 @@ Specifies whether bits are transmitted least-significant-bit first (LSB) or most

<h3>14: Mark/Space Frequency</h3>

When unchecked, the mark frequency is the higher frequency, when checked the space frequency is higher.
When unchecked, the mark frequency is the higher RF frequency, when checked the space frequency is higher.

This should be unchecked when transmitter is using LSB AFSK and checked for USB AFSK and DWD
[1](https://www.dwd.de/EN/specialusers/shipping/broadcast_en/brodcast_rtty_1_052014.pdf?__blob=publicationFile&v=1)
[2](https://www.dwd.de/EN/specialusers/shipping/broadcast_en/broadcast_rtty_2_052014.pdf?__blob=publicationFile&v=1)
shipping weather broadcasts.

<h3>15: Suppress CR LF</h3>

Expand All @@ -101,3 +106,4 @@ Click to specify the name of the .txt file which received characters are logged

The received text area shows characters as they are received.

Holding the cursor over an acronym may show a tooltip with the decoded acronym.
3 changes: 3 additions & 0 deletions plugins/channelrx/demodrtty/rttydemodgui.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,7 @@
#include "plugin/pluginapi.h"
#include "util/simpleserializer.h"
#include "util/db.h"
#include "util/rtty.h"
#include "gui/basicchannelsettingsdialog.h"
#include "gui/devicestreamselectiondialog.h"
#include "dsp/dspengine.h"
Expand Down Expand Up @@ -482,6 +483,8 @@ RttyDemodGUI::RttyDemodGUI(PluginAPI* pluginAPI, DeviceUISet *deviceUISet, Baseb
connect(&m_channelMarker, SIGNAL(highlightedByCursor()), this, SLOT(channelMarkerHighlightedByCursor()));
connect(getInputMessageQueue(), SIGNAL(messageEnqueued()), this, SLOT(handleInputMessages()));

ui->text->addAcronyms(Rtty::m_acronyms);

ui->scopeContainer->setVisible(false);

// Hide developer only settings
Expand Down
8 changes: 7 additions & 1 deletion plugins/channelrx/demodrtty/rttydemodgui.ui
Original file line number Diff line number Diff line change
Expand Up @@ -916,7 +916,7 @@
</property>
<layout class="QVBoxLayout" name="verticalLayout_2">
<item>
<widget class="QPlainTextEdit" name="text">
<widget class="AcronymView" name="text">
<property name="toolTip">
<string>Received text</string>
</property>
Expand Down Expand Up @@ -1293,6 +1293,12 @@
<header>gui/glscopegui.h</header>
<container>1</container>
</customwidget>
<customwidget>
<class>AcronymView</class>
<extends>QTextEdit</extends>
<header>gui/acronymview.h</header>
<container>1</container>
</customwidget>
</customwidgets>
<tabstops>
<tabstop>deltaFrequency</tabstop>
Expand Down
6 changes: 4 additions & 2 deletions plugins/channelrx/demodrtty/rttydemodsink.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -154,8 +154,8 @@ void RttyDemodSink::processOneSample(Complex &ci)
m_expIdx = (m_expIdx + 1) % m_expLength;
//Complex exp = m_exp[m_sampleIdx];
//qDebug() << "IQ " << real(ci) << imag(ci);
Complex corr1 = ci * exp;
Complex corr2 = ci * std::conj(exp);
Complex corr1 = ci * std::conj(exp); // Conj is high/mark freq (as for matched filter, we need to time reverse and take conjugate)
Complex corr2 = ci * exp; // Low/space freq

// Filter
Real abs1, abs2;
Expand Down Expand Up @@ -238,6 +238,8 @@ void RttyDemodSink::processOneSample(Complex &ci)
m_clockCount = 0;
m_clock = false;
m_cycleCount = 0;
m_rssiMagSqSum = 0.0;
m_rssiMagSqCount = 0;
}
}
else
Expand Down
4 changes: 4 additions & 0 deletions plugins/channeltx/CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -1,5 +1,9 @@
project(mod)

if (ENABLE_CHANNELTX_MODRTTY)
add_subdirectory(modrtty)
endif()

if (ENABLE_CHANNELTX_MODAIS)
add_subdirectory(modais)
endif()
Expand Down
4 changes: 4 additions & 0 deletions plugins/channeltx/modpacket/packetmodgui.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -288,6 +288,7 @@ void PacketModGUI::preEmphasisSelect(const QPoint& p)
{
FMPreemphasisDialog dialog(m_settings.m_preEmphasisTau, m_settings.m_preEmphasisHighFreq);
dialog.move(p);
new DialogPositioner(&dialog, false);

if (dialog.exec() == QDialog::Accepted)
{
Expand All @@ -301,6 +302,7 @@ void PacketModGUI::bpfSelect(const QPoint& p)
{
PacketModBPFDialog dialog(m_settings.m_bpfLowCutoff, m_settings.m_bpfHighCutoff, m_settings.m_bpfTaps);
dialog.move(p);
new DialogPositioner(&dialog, false);

if (dialog.exec() == QDialog::Accepted)
{
Expand All @@ -315,6 +317,7 @@ void PacketModGUI::repeatSelect(const QPoint& p)
{
PacketModRepeatDialog dialog(m_settings.m_repeatDelay, m_settings.m_repeatCount);
dialog.move(p);
new DialogPositioner(&dialog, false);

if (dialog.exec() == QDialog::Accepted)
{
Expand All @@ -339,6 +342,7 @@ void PacketModGUI::txSettingsSelect(const QPoint& p)
m_settings.m_writeToFile);

dialog.move(p);
new DialogPositioner(&dialog, false);

if (dialog.exec() == QDialog::Accepted)
{
Expand Down
2 changes: 1 addition & 1 deletion plugins/channeltx/modpacket/packetmodsource.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -349,7 +349,7 @@ void PacketModSource::applySettings(const PacketModSettings& settings, bool forc
<< " symbolSpan: " << settings.m_symbolSpan
<< " channelSampleRate:" << m_channelSampleRate
<< " baud:" << settings.m_baud;
m_pulseShape.create(settings.m_beta, m_settings.m_symbolSpan, m_channelSampleRate/settings.m_baud);
m_pulseShape.create(settings.m_beta, settings.m_symbolSpan, m_channelSampleRate/settings.m_baud);
}
if ((settings.m_polynomial != m_settings.m_polynomial) || force)
m_scrambler.setPolynomial(settings.m_polynomial);
Expand Down
69 changes: 69 additions & 0 deletions plugins/channeltx/modrtty/CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,69 @@
project(modrtty)

set(modrtty_SOURCES
rttymod.cpp
rttymodbaseband.cpp
rttymodsource.cpp
rttymodplugin.cpp
rttymodsettings.cpp
rttymodwebapiadapter.cpp
)

set(modrtty_HEADERS
rttymod.h
rttymodbaseband.h
rttymodsource.h
rttymodplugin.h
rttymodsettings.h
rttymodwebapiadapter.h
)

include_directories(
${CMAKE_SOURCE_DIR}/swagger/sdrangel/code/qt5/client
)

if(NOT SERVER_MODE)
set(modrtty_SOURCES
${modrtty_SOURCES}
rttymodgui.cpp
rttymodgui.ui
rttymodrepeatdialog.cpp
rttymodrepeatdialog.ui
rttymodtxsettingsdialog.cpp
rttymodtxsettingsdialog.ui
)
set(modrtty_HEADERS
${modrtty_HEADERS}
rttymodgui.h
rttymodrepeatdialog.h
rttymodtxsettingsdialog.h
)
set(TARGET_NAME modrtty)
set(TARGET_LIB "Qt::Widgets")
set(TARGET_LIB_GUI "sdrgui")
set(INSTALL_FOLDER ${INSTALL_PLUGINS_DIR})
else()
set(TARGET_NAME modrttysrv)
set(TARGET_LIB "")
set(TARGET_LIB_GUI "")
set(INSTALL_FOLDER ${INSTALL_PLUGINSSRV_DIR})
endif()

add_library(${TARGET_NAME} SHARED
${modrtty_SOURCES}
)

target_link_libraries(${TARGET_NAME}
Qt::Core
${TARGET_LIB}
sdrbase
${TARGET_LIB_GUI}
swagger
)

install(TARGETS ${TARGET_NAME} DESTINATION ${INSTALL_FOLDER})

# Install debug symbols
if (WIN32)
install(FILES $<TARGET_PDB_FILE:${TARGET_NAME}> CONFIGURATIONS Debug RelWithDebInfo DESTINATION ${INSTALL_FOLDER} )
endif()
138 changes: 138 additions & 0 deletions plugins/channeltx/modrtty/readme.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,138 @@
<h1>RTTY Modulator Plugin</h1>

<h2>Introduction</h2>

This plugin can be used to modulate RTTY (Radioteletype) encoded text.
RTTY uses BFSK (Binary Frequency Shift Keying), where transmission of data alternates between two frequencies,
the mark frequency and the space frequency. The RTTY Modulator should be centered in between these frequencies.
The baud rate, frequency shift (difference between mark and space frequencies), filter bandwidth and baudot character set are configurable.

<h2>Interface</h2>

The top and bottom bars of the channel window are described [here](../../../sdrgui/channel/readme.md)

![RTTY Modulator plugin GUI](../../../doc/img/RTTYMod_plugin.png)

<h3>1: Frequency shift from center frequency of transmission</h3>

Use the wheels to adjust the frequency shift in Hz from the center frequency of transmission. Left click on a digit sets the cursor position at this digit. Right click on a digit sets all digits on the right to zero. This effectively floors value at the digit position. Wheels are moved with the mousewheel while pointing at the wheel or by selecting the wheel with the left mouse click and using the keyboard arrows. Pressing shift simultaneously moves digit by 5 and pressing control moves it by 2.

<h3>2: Channel power</h3>

Average total power in dB relative to a +/- 1.0 amplitude signal generated in the pass band.

<h3>3: Channel mute</h3>

Use this button to toggle mute for this channel.

<h3>4: Mode</h3>

Contains a list of common baud rate and frequency shift settings. To specify your own, set this option to Custom.

45.45/170 is common for amateur RTTY.

<h3>5: Baud</h3>

Specifies the baud rate in symbols (bits) per second.

<h3>6: Frequency Shift</h3>

Adjusts the frequency shift (different between mark and space frequencies) in Hz.

<h3>7: RF Bandwidth</h3>

This specifies the bandwidth of a LPF that is applied to the output signal to limit the RF bandwidth.

<h3>8: Gain</h3>

Adjusts the gain in dB from -60 to 0dB.

<h3>9: Level meter in %</h3>

- top bar (beige): average value
- bottom bar (brown): instantaneous peak value
- tip vertical bar (bright red): peak hold value

<h3>10: UDP</h3>

When checked, a UDP port is opened to receive text from other features or applications that will be transmitted.

<h3>11: UDP address</h3>

IP address of the interface to open the UDP port on, to receive text to be transmitted.

<h3>12: UDP port</h3>

UDP port number to receive text to be transmitted on.

<h3>13: Baudot Character Set</h3>

Specifies the Baudot character set used to encode the text to transmit. The following character sets are supported:

* ITA 2
* UK
* European
* US
* Russian
* Murray

<h3>14: Bit Ordering</h3>

Specifies whether bits are transmitted least-significant-bit first (LSB) or most-significant-bit first (MSB).

<h3>15: Mark/Space Frequency</h3>

When unchecked, the mark frequency is the higher RF frequency, when checked the space frequency is higher.

<h3>16: Unshift on Space</h3>

When checked, the Baudot character set will shift to letters when a space character (' ') is transmitted.

<h3>17: Repeat</h3>

Check this button to repeatedly transmit a packet. Right click to open the dialog to adjust the number of times the packet should be repeated.

<h3>18: Clear Transmitted Text</h3>

Press to clear the transmitted text.

<h3>19: Text to Transmit</h3>

Enter text to transmit. Pressing return will transmit the text and clear this field. Press the arrow to display and select a list of pre-defined text or previously transmitted text to enter in to the field.

The list of pre-defined text can be customised via the Transmit Settings dialog (20).

<h3>20: TX</h3>

Press to transmit the current text. The text field will not be cleared.

Right click to open a dialog to adjust additional Transmit Settings, including the list of pre-defined text.

Predefined text supports the following variable substitutions:

* ${callsign} - Gets replaced with the station name from Preferences > My Position
* ${location} = Gets replaced with the Maidenhead locator for the position specified under Preferences > My Position

The substitutions are applied when the Transmit Settings dialog is closed.

<h3>21: Transmitted Text</h3>

The trasnmitted text area shows characters as they are transmitted.

Holding the cursor over an acronym may show a tooltip with the decoded acronym.

<h2>API</h2>

Full details of the API can be found in the Swagger documentation. Below are a few examples.

To transmit the current text simply send a "tx" action:

curl -X POST "http://127.0.0.1:8091/sdrangel/deviceset/0/channel/0/actions" -d '{"channelType": "RTTYMod", "direction": 1, "RTTYModActions": { "tx": 1 }}'

To transmit text specified on the command line:

curl -X POST "http://127.0.0.1:8091/sdrangel/deviceset/0/channel/0/actions" -d '{"channelType": "RTTYMod", "direction": 1, "RTTYModActions": { "tx": 1, "payload": {"text": "CQ CQ CQ anyone using SDRangel CQ" }}}'

To set the baud rate and frequency shift:

curl -X PATCH "http://127.0.0.1:8091/sdrangel/deviceset/0/channel/0/settings" -d '{"channelType": "RTTYMod", "direction": 1, "RTTYModSettings": {"baud": 45.45, "frequencyShift": 170 }}'
Loading

0 comments on commit 74977c8

Please sign in to comment.