This commit is contained in:
wu58430 2023-12-25 13:43:25 +08:00
parent 60f6f0ec3b
commit 38aec1624f
21 changed files with 386 additions and 358 deletions

View File

@ -20,7 +20,7 @@
</configurations>
</component>
<component name="ChangeListManager">
<list default="true" id="cea36e80-e289-4d69-9030-7186d540ac0e" name="更改" comment="中文" />
<list default="true" id="cea36e80-e289-4d69-9030-7186d540ac0e" name="更改" comment="fix show" />
<option name="SHOW_DIALOG" value="false" />
<option name="HIGHLIGHT_CONFLICTS" value="true" />
<option name="HIGHLIGHT_NON_ACTIVE_CHANGELIST" value="false" />
@ -95,11 +95,6 @@
</key>
</component>
<component name="RunManager" selected="Shell Script.win docker">
<configuration default="true" type="CLionExternalRunConfiguration" factoryName="Application" REDIRECT_INPUT="false" ELEVATE="false" USE_EXTERNAL_CONSOLE="false" PASS_PARENT_ENVS_2="true">
<method v="2">
<option name="CLION.EXTERNAL.BUILD" enabled="true" />
</method>
</configuration>
<configuration name="clean" type="MAKEFILE_TARGET_RUN_CONFIGURATION" factoryName="Makefile" temporary="true">
<makefile filename="$PROJECT_DIR$/Makefile" target="clean" workingDirectory="" arguments="">
<envs />
@ -240,22 +235,7 @@
<workItem from="1703259169230" duration="73000" />
<workItem from="1703259273867" duration="8810000" />
<workItem from="1703380739516" duration="6230000" />
<workItem from="1703411329993" duration="1576000" />
<workItem from="1703419616449" duration="4000" />
</task>
<task id="LOCAL-00048" summary="MDC RX">
<created>1701693594928</created>
<option name="number" value="00048" />
<option name="presentableId" value="LOCAL-00048" />
<option name="project" value="LOCAL" />
<updated>1701693594928</updated>
</task>
<task id="LOCAL-00049" summary="写频">
<created>1701736695809</created>
<option name="number" value="00049" />
<option name="presentableId" value="LOCAL-00049" />
<option name="project" value="LOCAL" />
<updated>1701736695809</updated>
<workItem from="1703411329993" duration="17361000" />
</task>
<task id="LOCAL-00050" summary="写频">
<created>1701737194492</created>
@ -586,7 +566,21 @@
<option name="project" value="LOCAL" />
<updated>1703258782152</updated>
</task>
<option name="localTasksCounter" value="97" />
<task id="LOCAL-00097" summary="中文">
<created>1703412914805</created>
<option name="number" value="00097" />
<option name="presentableId" value="LOCAL-00097" />
<option name="project" value="LOCAL" />
<updated>1703412914805</updated>
</task>
<task id="LOCAL-00098" summary="fix show">
<created>1703482452046</created>
<option name="number" value="00098" />
<option name="presentableId" value="LOCAL-00098" />
<option name="project" value="LOCAL" />
<updated>1703482452046</updated>
</task>
<option name="localTasksCounter" value="99" />
<servers />
</component>
<component name="TypeScriptGeneratedFilesManager">
@ -613,7 +607,6 @@
</option>
</component>
<component name="VcsManagerConfiguration">
<MESSAGE value="test create" />
<MESSAGE value="reduce flash" />
<MESSAGE value="rebuild chinese" />
<MESSAGE value="MDC RX" />
@ -638,7 +631,8 @@
<MESSAGE value="中英文字符对齐" />
<MESSAGE value="支持中文编译选项ENABLE_CHINESE_FULL" />
<MESSAGE value="中文" />
<option name="LAST_COMMIT_MESSAGE" value="中文" />
<MESSAGE value="fix show" />
<option name="LAST_COMMIT_MESSAGE" value="fix show" />
</component>
<component name="XDebuggerManager">
<breakpoint-manager>

17
Doxyfile Normal file
View File

@ -0,0 +1,17 @@
OUTPUT_DIRECTORY = docs
GENERATE_LATEX = NO
GENERATE_RTF = NO
GENERATE_MAN = NO
OPTIMIZE_OUTPUT_FOR_C = YES
HAVE_DOT = YES
EXTRACT_ALL = YES
EXTRACT_PRIVATE = YES
EXTRACT_STATIC = YES
CALL_GRAPH = YES
CALLER_GRAPH = YES
DISABLE_INDEX = YES
GENERATE_TREEVIEW = YES
RECURSIVE = YES
COLLABORATION_GRAPH = YES
GRAPHICAL_HIERARCHY = YES
DOT_MULTI_TARGETS = YES

View File

@ -48,6 +48,7 @@ ENABLE_MDC1200 ?= 1
ENABLE_MDC1200_SHOW_OP_ARG ?= 1
ENABLE_MDC1200_SIDE_BEEP ?= 0
ENABLE_MDC1200_CONTACT ?= 1
ENABLE_CHINESE_FULL =0
@ -215,6 +216,11 @@ ifneq (, $(shell $(WHERE) git))
VERSION_STRING := $(shell git rev-parse --short HEAD)
endif
endif
# If there is still no VERSION_STRING we need to make one.
# It is needed for the firmware packing script
ifeq (, $(VERSION_STRING))
VERSION_STRING := NOGIT
endif
#VERSION_STRING := 230930b
@ -262,6 +268,7 @@ endif
ifeq ($(ENABLE_MDC1200_CONTACT),1)
CFLAGS += -DENABLE_MDC1200_CONTACT
endif
CFLAGS += -DENABLE_CHINESE_FULL=$(ENABLE_CHINESE_FULL)
ifeq ($(ENABLE_MDC1200_SHOW_OP_ARG),1)
@ -466,6 +473,8 @@ ifdef OS
else
clean:
$(RM) $(call FixPath, $(TARGET).bin $(TARGET).packed.bin $(TARGET) $(OBJS) $(DEPS))
doxygen:
doxygen
endif
else
clean:

116
app/app.c
View File

@ -732,16 +732,15 @@ static void CheckRadioInterrupts(void)
}
}
void APP_EndTransmission(void)
{ // back to RX mode
{
// back to RX mode
RADIO_SendEndOfTransmission();
// send the CTCSS/DCS tail tone - allows the receivers to mute the usual FM squelch tail/crash
RADIO_EnableCxCSS();
RADIO_SetupRegisters(false);
if (gMonitor)
gFlagReconfigureVfos = true; //turn the monitor back on
if (gMonitor) {
//turn the monitor back on
gFlagReconfigureVfos = true;
}
}
#ifdef ENABLE_VOX
static void HandleVox(void)
{
@ -883,37 +882,32 @@ void APP_Update(void)
#endif
// toggle between the VFO's if dual watch is enabled
if (!SCANNER_IsScanning() && gEeprom.DUAL_WATCH != DUAL_WATCH_OFF)
{
if (!SCANNER_IsScanning()
&& gEeprom.DUAL_WATCH != DUAL_WATCH_OFF
&& gScheduleDualWatch
&& gScanStateDir == SCAN_OFF
&& !gPttIsPressed
&& gCurrentFunction != FUNCTION_POWER_SAVE
#ifdef ENABLE_VOICE
if (gScheduleDualWatch && gVoiceWriteIndex == 0)
#else
if (gScheduleDualWatch)
&& gVoiceWriteIndex == 0
#endif
{
if (gScanStateDir == SCAN_OFF)
{
if (!gPttIsPressed &&
#ifdef ENABLE_FMRADIO
!gFmRadioMode &&
#endif
#ifdef ENABLE_DTMF_CALLING
gDTMF_CallState == DTMF_CALL_STATE_NONE &&
#endif
gCurrentFunction != FUNCTION_POWER_SAVE)
{
DualwatchAlternate(); // toggle between the two VFO's
#ifdef ENABLE_FMRADIO
&& !gFmRadioMode
#endif
#ifdef ENABLE_DTMF_CALLING
&& gDTMF_CallState == DTMF_CALL_STATE_NONE
#endif
) {
DualwatchAlternate(); // toggle between the two VFO's
if (gRxVfoIsActive && gScreenToDisplay == DISPLAY_MAIN)
GUI_SelectNextDisplay(DISPLAY_MAIN);
gRxVfoIsActive = false;
gScanPauseMode = false;
gRxReceptionMode = RX_MODE_NONE;
gScheduleDualWatch = false;
}
}
if (gRxVfoIsActive && gScreenToDisplay == DISPLAY_MAIN) {
GUI_SelectNextDisplay(DISPLAY_MAIN);
}
gRxVfoIsActive = false;
gScanPauseMode = false;
gRxReceptionMode = RX_MODE_NONE;
gScheduleDualWatch = false;
}
#ifdef ENABLE_FMRADIO
@ -930,39 +924,31 @@ void APP_Update(void)
#endif
if (gSchedulePowerSave) {
if (gPttIsPressed ||
gKeyBeingHeld ||
gEeprom.BATTERY_SAVE == 0 ||
gScanStateDir != SCAN_OFF ||
gCssBackgroundScan ||
gScreenToDisplay != DISPLAY_MAIN
if (gPttIsPressed
|| gKeyBeingHeld
|| gEeprom.BATTERY_SAVE == 0
|| gScanStateDir != SCAN_OFF
|| gCssBackgroundScan
|| gScreenToDisplay != DISPLAY_MAIN
#ifdef ENABLE_FMRADIO
|| gFmRadioMode
#endif
#ifdef ENABLE_DTMF_CALLING
|| gDTMF_CallState != DTMF_CALL_STATE_NONE
#endif
){
gBatterySaveCountdown_10ms = battery_save_count_10ms;
}
else
#ifdef ENABLE_NOAA
if ((!IS_NOAA_CHANNEL(gEeprom.ScreenChannel[0]) && !IS_NOAA_CHANNEL(gEeprom.ScreenChannel[1])) || !gIsNoaaMode)
|| (gIsNoaaMode && (IS_NOAA_CHANNEL(gEeprom.ScreenChannel[0]) || IS_NOAA_CHANNEL(gEeprom.ScreenChannel[1])))
#endif
{
//if (gCurrentFunction != FUNCTION_POWER_SAVE)
) {
gBatterySaveCountdown_10ms = battery_save_count_10ms;
} else {
FUNCTION_Select(FUNCTION_POWER_SAVE);
}
#ifdef ENABLE_NOAA
else
{
gBatterySaveCountdown_10ms = battery_save_count_10ms;
}
#else
gSchedulePowerSave = false;
#endif
}
gSchedulePowerSave = false;
}
if (gPowerSaveCountdownExpired && gCurrentFunction == FUNCTION_POWER_SAVE
#ifdef ENABLE_VOICE
@ -1023,16 +1009,17 @@ void APP_Update(void)
// called every 10ms
static void CheckKeys(void)
{
if (0
#ifdef ENABLE_DTMF_CALLING
|| gSetting_KILLED
if(gSetting_KILLED){
return;
}
#endif
#ifdef ENABLE_AIRCOPY
|| (gScreenToDisplay == DISPLAY_AIRCOPY && gAircopyState != AIRCOPY_READY)
if (gScreenToDisplay == DISPLAY_AIRCOPY && gAircopyState != AIRCOPY_READY){
return;
}
#endif
)
return;
// -------------------- PTT ------------------------
@ -1578,9 +1565,8 @@ static void ALARM_Off(void)
AUDIO_AudioPathOff();
gEnableSpeaker = false;
if (gAlarmState == ALARM_STATE_TXALARM) {
RADIO_SendEndOfTransmission();
RADIO_EnableCxCSS();
if (gAlarmState == ALARM_STATE_TXALARM || gAlarmState == ALARM_STATE_TX1750) {
RADIO_SendEndOfTransmission();
}
gAlarmState = ALARM_STATE_OFF;

View File

@ -114,23 +114,16 @@ bool DTMF_GetContact(const int Index, char *pContact)
bool DTMF_FindContact(const char *pContact, char *pResult)
{
char Contact[16];
unsigned int i;
pResult[0] = 0;
for (i = 0; i < MAX_DTMF_CONTACTS; i++)
{
unsigned int j;
if (!DTMF_GetContact(i, Contact))
for (unsigned int i = 0; i < MAX_DTMF_CONTACTS; i++) {
char Contact[16];
if (!DTMF_GetContact(i, Contact)) {
return false;
}
for (j = 0; j < 3; j++)
if (pContact[j] != Contact[j + 8])
break;
if (j == 3)
{
memcpy(pResult, Contact, 8);
if (memcmp(pContact, Contact + 8, 3) == 0) {
memcpy(pResult, Contact, 8);
pResult[8] = 0;
return true;
}
@ -478,4 +471,39 @@ gCurrentVfo->DTMF_PTT_ID_TX_MODE == PTT_ID_TX_DOWN)
BK4819_ExitDTMF_TX(false);
return true;
}
void DTMF_SendEndOfTransmission(void)
{
if (gCurrentVfo->DTMF_PTT_ID_TX_MODE == PTT_ID_APOLLO) {
BK4819_PlaySingleTone(2475, 250, 28, gEeprom.DTMF_SIDE_TONE);
}
if ((gCurrentVfo->DTMF_PTT_ID_TX_MODE == PTT_ID_TX_DOWN || gCurrentVfo->DTMF_PTT_ID_TX_MODE == PTT_ID_BOTH)
#ifdef ENABLE_DTMF_CALLING
&& gDTMF_CallState == DTMF_CALL_STATE_NONE
#endif
) { // end-of-tx
if (gEeprom.DTMF_SIDE_TONE)
{
AUDIO_AudioPathOn();
gEnableSpeaker = true;
SYSTEM_DelayMs(60);
}
BK4819_EnterDTMF_TX(gEeprom.DTMF_SIDE_TONE);
BK4819_PlayDTMFString(
gEeprom.DTMF_DOWN_CODE,
0,
gEeprom.DTMF_FIRST_CODE_PERSIST_TIME,
gEeprom.DTMF_HASH_CODE_PERSIST_TIME,
gEeprom.DTMF_CODE_PERSIST_TIME,
gEeprom.DTMF_CODE_INTERVAL_TIME);
AUDIO_AudioPathOff();
gEnableSpeaker = false;
}
BK4819_ExitDTMF_TX(true);
}

View File

@ -105,7 +105,7 @@ char DTMF_GetCharacter(const unsigned int code);
void DTMF_clear_input_box(void);
void DTMF_Append(const char vode);
bool DTMF_Reply();
void DTMF_SendEndOfTransmission(void);
#ifdef ENABLE_DTMF_CALLING
void DTMF_clear_RX(void);
DTMF_CallMode_t DTMF_CheckGroupCall(const char *pDTMF, const unsigned int size);

View File

@ -16,6 +16,7 @@
#include "app/spectrum.h"
#include "am_fix.h"
#include "audio.h"
#include "misc.h"
#ifdef ENABLE_SCAN_RANGES
#include "chFrScanner.h"
@ -37,7 +38,6 @@ struct FrequencyBandInfo {
const uint16_t RSSI_MAX_VALUE = 65535;
static uint16_t R30, R37, R3D, R43, R47, R48, R7E;
static uint32_t initialFreq;
static char String[32];
@ -221,24 +221,29 @@ static void ToggleAFBit(bool on) {
BK4819_WriteRegister(BK4819_REG_47, reg);
}
static const BK4819_REGISTER_t registers_to_save[] ={
BK4819_REG_30,
BK4819_REG_37,
BK4819_REG_3D,
BK4819_REG_43,
BK4819_REG_47,
BK4819_REG_48,
BK4819_REG_7E,
};
static uint16_t registers_stack [sizeof(registers_to_save)];
static void BackupRegisters() {
R30 = BK4819_ReadRegister(BK4819_REG_30);
R37 = BK4819_ReadRegister(BK4819_REG_37);
R3D = BK4819_ReadRegister(BK4819_REG_3D);
R43 = BK4819_ReadRegister(BK4819_REG_43);
R47 = BK4819_ReadRegister(BK4819_REG_47);
R48 = BK4819_ReadRegister(BK4819_REG_48);
R7E = BK4819_ReadRegister(BK4819_REG_7E);
for (uint32_t i = 0; i < ARRAY_SIZE(registers_to_save); i++){
registers_stack[i] = BK4819_ReadRegister(registers_to_save[i]);
}
}
static void RestoreRegisters() {
BK4819_WriteRegister(BK4819_REG_30, R30);
BK4819_WriteRegister(BK4819_REG_37, R37);
BK4819_WriteRegister(BK4819_REG_3D, R3D);
BK4819_WriteRegister(BK4819_REG_43, R43);
BK4819_WriteRegister(BK4819_REG_47, R47);
BK4819_WriteRegister(BK4819_REG_48, R48);
BK4819_WriteRegister(BK4819_REG_7E, R7E);
for (uint32_t i = 0; i < ARRAY_SIZE(registers_to_save); i++){
BK4819_WriteRegister(registers_to_save[i], registers_stack[i]);
}
}
static void ToggleAFDAC(bool on) {
@ -483,13 +488,12 @@ static void UpdateDBMax(bool inc) {
}
static void UpdateScanStep(bool inc) {
if (inc && settings.scanStepIndex < S_STEP_100_0kHz) {
settings.scanStepIndex++;
} else if (!inc && settings.scanStepIndex > 0) {
settings.scanStepIndex--;
if (inc) {
settings.scanStepIndex = settings.scanStepIndex != S_STEP_100_0kHz ? settings.scanStepIndex + 1 : 0;
} else {
return;
settings.scanStepIndex = settings.scanStepIndex != 0 ? settings.scanStepIndex - 1 : S_STEP_100_0kHz;
}
settings.frequencyChangeStep = GetBW() >> 1;
RelaunchScan();
ResetBlacklist();

View File

@ -17,7 +17,7 @@
#ifndef BK4819_REGS_H
#define BK4819_REGS_H
#include <stdint.h>
typedef struct {
const char *name;
uint8_t num;

View File

@ -14,8 +14,10 @@
* limitations under the License.
*/
#include <stdio.h> // NULL
#include <stdint.h>
#include <stdio.h>
#include "settings.h"
#include "../audio.h"
#include "../bsp/dp32g030/gpio.h"
#include "../bsp/dp32g030/portcon.h"
@ -26,6 +28,7 @@
#ifdef ENABLE_MDC1200
#include "app/mdc1200.h"
#endif
#include "misc.h"
#ifndef ARRAY_SIZE
#define ARRAY_SIZE(x) (sizeof(x) / sizeof(x[0]))
#endif
@ -325,6 +328,22 @@ void BK4819_InitAGC(bool amModulation)
}
void BK4819_PlayRoger(void)
{
if (gEeprom.ROGER == ROGER_MODE_ROGER||gEeprom.ROGER==ROGER_MODE_MDC_HEAD_ROGER)
BK4819_PlayRogerNormal();
else
if (gEeprom.ROGER == ROGER_MODE_MDC_END||gEeprom.ROGER==ROGER_MODE_MDC_BOTH) {
BK4819_send_MDC1200(MDC1200_OP_CODE_POST_ID, 0x00, gEeprom.MDC1200_ID, false);
#ifdef ENABLE_MDC1200_SIDE_BEEP
BK4819_start_tone(880, 10, true, true);
SYSTEM_DelayMs(120);
BK4819_stop_tones(true);
#endif
}
}
int8_t BK4819_GetRxGain_dB(void)
{
union {
@ -609,90 +628,54 @@ void BK4819_SetFilterBandwidth(const BK4819_FilterBandwidth_t Bandwidth, const b
//
// <1:0> 0 ???
uint16_t val;
m_bandwidth = Bandwidth;
uint16_t val = 0;
switch (Bandwidth)
{
default:
case BK4819_FILTER_BW_WIDE: // 25kHz
if (weak_no_different)
{ // make the RX bandwidth the same with weak signals
val =
(0u << 15) | // 0
(4u << 12) | // *3 RF filter bandwidth
(4u << 9) | // *0 RF filter bandwidth when signal is weak
(6u << 6) | // *0 AFTxLPF2 filter Band Width
(2u << 4) | // 2 BW Mode Selection
(1u << 3) | // 1
(0u << 2) | // 0 Gain after FM Demodulation
(0u << 0); // 0
}
else
{ // with weak RX signals the RX bandwidth is reduced
val = // 0x3028); // 0 011 000 000 10 1 0 00
(0u << 15) | // 0
(4u << 12) | // *3 RF filter bandwidth
(2u << 9) | // *0 RF filter bandwidth when signal is weak
(6u << 6) | // *0 AFTxLPF2 filter Band Width
(2u << 4) | // 2 BW Mode Selection
(1u << 3) | // 1
(0u << 2) | // 0 Gain after FM Demodulation
(0u << 0); // 0
val = (4u << 12) | // *3 RF filter bandwidth
(6u << 6) | // *0 AFTxLPF2 filter Band Width
(2u << 4) | // 2 BW Mode Selection
(1u << 3) | // 1
(0u << 2); // 0 Gain after FM Demodulation
if (weak_no_different) {
// make the RX bandwidth the same with weak signals
val |= (4u << 9); // *0 RF filter bandwidth when signal is weak
} else {
/// with weak RX signals the RX bandwidth is reduced
val |= (2u << 9); // *0 RF filter bandwidth when signal is weak
}
break;
case BK4819_FILTER_BW_NARROW: // 12.5kHz
if (weak_no_different)
{
val =
(0u << 15) | // 0
(4u << 12) | // *4 RF filter bandwidth
(4u << 9) | // *0 RF filter bandwidth when signal is weak
(0u << 6) | // *1 AFTxLPF2 filter Band Width
(0u << 4) | // 0 BW Mode Selection
(1u << 3) | // 1
(0u << 2) | // 0 Gain after FM Demodulation
(0u << 0); // 0
}
else
{
val = // 0x4048); // 0 100 000 001 00 1 0 00
(0u << 15) | // 0
(4u << 12) | // *4 RF filter bandwidth
(2u << 9) | // *0 RF filter bandwidth when signal is weak
(0u << 6) | // *1 AFTxLPF2 filter Band Width
(0u << 4) | // 0 BW Mode Selection
(1u << 3) | // 1
(0u << 2) | // 0 Gain after FM Demodulation
(0u << 0); // 0
val = (4u << 12) | // *4 RF filter bandwidth
(0u << 6) | // *1 AFTxLPF2 filter Band Width
(0u << 4) | // 0 BW Mode Selection
(1u << 3) | // 1
(0u << 2); // 0 Gain after FM Demodulation
if (weak_no_different) {
val |= (4u << 9); // *0 RF filter bandwidth when signal is weak
} else {
val |= (2u << 9);
}
break;
case BK4819_FILTER_BW_NARROWER: // 6.25kHz
if (weak_no_different)
{
val =
(0u << 15) | // 0
(3u << 12) | // 3 RF filter bandwidth
(3u << 9) | // *0 RF filter bandwidth when signal is weak
(1u << 6) | // 1 AFTxLPF2 filter Band Width
(1u << 4) | // 1 BW Mode Selection
(1u << 3) | // 1
(0u << 2) | // 0 Gain after FM Demodulation
(0u << 0); // 0
}
else
{
val =
(0u << 15) | // 0
(3u << 12) | // 3 RF filter bandwidth
(0u << 9) | // 0 RF filter bandwidth when signal is weak
(1u << 6) | // 1 AFTxLPF2 filter Band Width
(1u << 4) | // 1 BW Mode Selection
(1u << 3) | // 1
(0u << 2) | // 1 Gain after FM Demodulation
(0u << 0); // 0
val = (3u << 12) | // 3 RF filter bandwidth
(3u << 9) | // *0 RF filter bandwidth when signal is weak
(1u << 6) | // 1 AFTxLPF2 filter Band Width
(1u << 4) | // 1 BW Mode Selection
(1u << 3) | // 1
(0u << 2); // 0 Gain after FM Demodulation
if (weak_no_different) {
val |= (3u << 9);
} else {
val |= (0u << 9); // 0 RF filter bandwidth when signal is weak
}
break;
}
@ -1268,36 +1251,48 @@ void BK4819_EnableTXLink(void)
BK4819_REG_30_ENABLE_TX_DSP |
BK4819_REG_30_DISABLE_RX_DSP);
}
void BK4819_PlayDTMF(char Code)
{
uint16_t tone1 = 0;
uint16_t tone2 = 0;
struct DTMF_TonePair {
uint16_t tone1;
uint16_t tone2;
};
const struct DTMF_TonePair tones[] = {
{941, 1336},
{697, 1209},
{697, 1336},
{697, 1477},
{770, 1209},
{770, 1336},
{770, 1477},
{852, 1209},
{852, 1336},
{852, 1477},
{697, 1633},
{770, 1633},
{852, 1633},
{941, 1633},
{941, 1209},
{941, 1477},
};
const struct DTMF_TonePair *pSelectedTone = NULL;
switch (Code)
{
case '0': tone1 = 941; tone2 = 1336; break;
case '1': tone1 = 697; tone2 = 1209; break;
case '2': tone1 = 697; tone2 = 1336; break;
case '3': tone1 = 697; tone2 = 1477; break;
case '4': tone1 = 770; tone2 = 1209; break;
case '5': tone1 = 770; tone2 = 1336; break;
case '6': tone1 = 770; tone2 = 1477; break;
case '7': tone1 = 852; tone2 = 1209; break;
case '8': tone1 = 852; tone2 = 1336; break;
case '9': tone1 = 852; tone2 = 1477; break;
case 'A': tone1 = 697; tone2 = 1633; break;
case 'B': tone1 = 770; tone2 = 1633; break;
case 'C': tone1 = 852; tone2 = 1633; break;
case 'D': tone1 = 941; tone2 = 1633; break;
case '*': tone1 = 941; tone2 = 1209; break;
case '#': tone1 = 941; tone2 = 1477; break;
case '0'...'9': pSelectedTone = &tones[0 + Code - '0']; break;
case 'A'...'D': pSelectedTone = &tones[10 + Code - 'A']; break;
case '*': pSelectedTone = &tones[14]; break;
case '#': pSelectedTone = &tones[15]; break;
default: pSelectedTone = NULL;
}
if (tone1 > 0)
BK4819_WriteRegister(BK4819_REG_71, (((uint32_t)tone1 * 103244) + 5000) / 10000); // with rounding
if (tone2 > 0)
BK4819_WriteRegister(BK4819_REG_72, (((uint32_t)tone2 * 103244) + 5000) / 10000); // with rounding
if (pSelectedTone) {
BK4819_WriteRegister(BK4819_REG_71, (((uint32_t)pSelectedTone->tone1 * 103244) + 5000) / 10000); // with rounding
BK4819_WriteRegister(BK4819_REG_72, (((uint32_t)pSelectedTone->tone2 * 103244) + 5000) / 10000); // with rounding
}
}
void BK4819_PlayDTMFString(const char *pString, bool bDelayFirst, uint16_t FirstCodePersistTime, uint16_t HashCodePersistTime, uint16_t CodePersistTime, uint16_t CodeInternalTime)
@ -1717,8 +1712,8 @@ void BK4819_PrepareFSKReceive(void)
BK4819_WriteRegister(BK4819_REG_59, 0x3068);
}
void BK4819_PlayRoger(void)
{
void BK4819_PlayRogerNormal(void){
#if 0
const uint32_t tone1_Hz = 500;
const uint32_t tone2_Hz = 700;
@ -2426,4 +2421,4 @@ void BK4819_enable_mdc1200_rx(const bool enable)
//BK4819_ExitTxMute();
BK4819_WriteRegister(0x50, 0x3B20); // 0011 1011 0010 0000
}
#endif
#endif

View File

@ -160,8 +160,9 @@ uint8_t BK4819_GetCTCType(void);
void BK4819_SendFSKData(uint16_t *pData);
void BK4819_PrepareFSKReceive(void);
void BK4819_PlayRoger(void);
void BK4819_PlayRoger(void);
void BK4819_PlayRogerNormal(void);
void BK4819_PlayRogerMDC(void);
void BK4819_Enable_AfDac_DiscMode_TxDsp(void);

BIN
firmware Normal file

Binary file not shown.

4
font.c
View File

@ -16,7 +16,9 @@
#include "font.h"
bool menu_set_flag=false;
#if ENABLE_CHINESE_FULL ==4
bool audio_keep_flag=false;
#endif
#if 0
#elif 0

5
font.h
View File

@ -16,14 +16,15 @@
#ifndef FONT_H
#define FONT_H
#include "stdbool.h"
#include <stdint.h>
extern const uint8_t gFontChinese_out[2013];
#define CHN_FONT_WIDTH 11U
#define CHN_FONT_HIGH 12U
#define ENABLE_CHINESE_FULL 0
#if ENABLE_CHINESE_FULL ==4
extern bool audio_keep_flag;
#define MAX_EDIT_INDEX 13
#else
#define MAX_EDIT_INDEX 10

View File

@ -46,53 +46,50 @@
FUNCTION_Type_t gCurrentFunction;
inline bool FUNCTION_IsRx() {
bool FUNCTION_IsRx()
{
return gCurrentFunction == FUNCTION_MONITOR ||
gCurrentFunction == FUNCTION_INCOMING ||
gCurrentFunction == FUNCTION_RECEIVE;
}
void FUNCTION_Init(void) {
#ifdef ENABLE_NOAA
if (!IS_NOAA_CHANNEL(gRxVfo->CHANNEL_SAVE))
#endif
{
gCurrentCodeType = (gRxVfo->Modulation != MODULATION_FM) ? CODE_TYPE_OFF : gRxVfo->pRX->CodeType;
}
#ifdef ENABLE_NOAA
else
gCurrentCodeType = CODE_TYPE_CONTINUOUS_TONE;
void FUNCTION_Init(void)
{
g_CxCSS_TAIL_Found = false;
g_CDCSS_Lost = false;
g_CTCSS_Lost = false;
g_SquelchLost = false;
gFlagTailNoteEliminationComplete = false;
gTailNoteEliminationCountdown_10ms = 0;
gFoundCTCSS = false;
gFoundCDCSS = false;
gFoundCTCSSCountdown_10ms = 0;
gFoundCDCSSCountdown_10ms = 0;
gEndOfRxDetectedMaybe = false;
gCurrentCodeType = (gRxVfo->Modulation != MODULATION_FM) ? CODE_TYPE_OFF : gRxVfo->pRX->CodeType;
#ifdef ENABLE_VOX
g_VOX_Lost = false;
#endif
#ifdef ENABLE_DTMF_CALLING
DTMF_clear_RX();
#endif
g_CxCSS_TAIL_Found = false;
g_CDCSS_Lost = false;
g_CTCSS_Lost = false;
#ifdef ENABLE_VOX
g_VOX_Lost = false;
#endif
g_SquelchLost = false;
gFlagTailNoteEliminationComplete = false;
gTailNoteEliminationCountdown_10ms = 0;
gFoundCTCSS = false;
gFoundCDCSS = false;
gFoundCTCSSCountdown_10ms = 0;
gFoundCDCSSCountdown_10ms = 0;
gEndOfRxDetectedMaybe = false;
#ifdef ENABLE_NOAA
gNOAACountdown_10ms = 0;
if (IS_NOAA_CHANNEL(gRxVfo->CHANNEL_SAVE)) {
gCurrentCodeType = CODE_TYPE_CONTINUOUS_TONE;
}
#endif
gUpdateStatus = true;
}
void FUNCTION_Foreground(const FUNCTION_Type_t PreviousFunction) {
#ifdef ENABLE_DTMF_CALLING
if (gDTMF_ReplyState != DTMF_REPLY_NONE)
@ -155,7 +152,6 @@ void FUNCTION_Transmit() {
// clear the DTMF RX live decoder buffer
gDTMF_RX_live_timeout = 0;
gDTMF_RX_live_timeout = 0;
memset(gDTMF_RX_live, 0, sizeof(gDTMF_RX_live));
#if defined(ENABLE_FMRADIO)

2
main.c
View File

@ -302,7 +302,6 @@ void Main(void) {
// BootMode != BOOT_MODE_NORMAL)
// { // keys are pressed
// UI_DisplayReleaseKeys(BootMode);
BACKLIGHT_TurnOn();
while (KEYBOARD_Poll() != KEY_INVALID) // 500ms
{
}
@ -315,6 +314,7 @@ void Main(void) {
UI_DisplayWelcome();
boot_counter_10ms = 250;
while (boot_counter_10ms > 0) {
if (KEYBOARD_Poll() == KEY_EXIT) { // halt boot beeps

57
radio.c
View File

@ -13,6 +13,7 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#include "driver/bk4819-regs.h"
#include "driver/bk4819.h"
#include <stdint.h>
#include "app/mdc1200.h"
@ -52,7 +53,15 @@ const char gModulationStr[MODULATION_UKNOWN][4] = {
[MODULATION_RAW]="RAW"
#endif
};
void RADIO_SendEndOfTransmission(void)
{
BK4819_PlayRoger();
DTMF_SendEndOfTransmission();
// send the CTCSS/DCS tail tone - allows the receivers to mute the usual FM squelch tail/crash
RADIO_EnableCxCSS();
RADIO_SetupRegisters(false);
}
bool RADIO_CheckValidChannel(uint16_t Channel, bool bCheckScanList, uint8_t VFO)
{ // return true if the channel appears valid
@ -1104,51 +1113,3 @@ void RADIO_PrepareCssTX(void)
RADIO_EnableCxCSS();
RADIO_SetupRegisters(true);
}
void RADIO_SendEndOfTransmission(void)
{
if (gEeprom.ROGER == ROGER_MODE_ROGER||gEeprom.ROGER==ROGER_MODE_MDC_HEAD_ROGER)
BK4819_PlayRoger();
else
if (gEeprom.ROGER == ROGER_MODE_MDC_END||gEeprom.ROGER==ROGER_MODE_MDC_BOTH) {
BK4819_send_MDC1200(MDC1200_OP_CODE_POST_ID, 0x00, gEeprom.MDC1200_ID, false);
#ifdef ENABLE_MDC1200_SIDE_BEEP
BK4819_start_tone(880, 10, true, true);
SYSTEM_DelayMs(120);
BK4819_stop_tones(true);
#endif
}
if (gCurrentVfo->DTMF_PTT_ID_TX_MODE == PTT_ID_APOLLO)
{ BK4819_PlaySingleTone(2475, 250, 28, gEeprom.DTMF_SIDE_TONE);
}
if ((gCurrentVfo->DTMF_PTT_ID_TX_MODE == PTT_ID_TX_DOWN || gCurrentVfo->DTMF_PTT_ID_TX_MODE == PTT_ID_BOTH)
#ifdef ENABLE_DTMF_CALLING
&& gDTMF_CallState == DTMF_CALL_STATE_NONE
#endif
) { // end-of-tx
if (gEeprom.DTMF_SIDE_TONE)
{
AUDIO_AudioPathOn();
gEnableSpeaker = true;
SYSTEM_DelayMs(60);
}
BK4819_EnterDTMF_TX(gEeprom.DTMF_SIDE_TONE);
BK4819_PlayDTMFString(
gEeprom.DTMF_DOWN_CODE,
0,
gEeprom.DTMF_FIRST_CODE_PERSIST_TIME,
gEeprom.DTMF_HASH_CODE_PERSIST_TIME,
gEeprom.DTMF_CODE_PERSIST_TIME,
gEeprom.DTMF_CODE_INTERVAL_TIME);
AUDIO_AudioPathOff();
gEnableSpeaker = false;
}
BK4819_ExitDTMF_TX(true);
}

116
ui/main.c
View File

@ -19,8 +19,8 @@
#include <stdlib.h> // abs()
#include "driver/uart.h"
#include "app/dtmf.h"
#include "font.h"
#include "app/chFrScanner.h"
#ifdef ENABLE_AM_FIX
#include "am_fix.h"
#endif
@ -149,7 +149,14 @@ void UI_DisplayAudioBar(void)
uint8_t bars = 13 * sqrt_level / 124;
uint8_t *p_line = gFrameBuffer[line];
memset(p_line, 0, LCD_WIDTH);
#if ENABLE_CHINESE_FULL==4
if(audio_keep_flag)
{
// audio_keep_flag=false;
}else
#endif
memset(p_line, 0, LCD_WIDTH);
DrawLevelBar(62, line, bars);
@ -241,9 +248,24 @@ UI_PrintStringSmall(str, 2, 0, line);
uint8_t *pLine = (gEeprom.RX_VFO == 0) ? gFrameBuffer[2] : gFrameBuffer[6];
if (now)
#if ENABLE_CHINESE_FULL==0
memset(pLine, 0, 23);
DrawSmallAntennaAndBars(pLine, Level);
DrawSmallAntennaAndBars(pLine, Level);
#else
if(IS_MR_CHANNEL(gEeprom.ScreenChannel[vfo_num]) )
{
memset(gFrameBuffer[3], 0, 23);
DrawSmallAntennaAndBars(gFrameBuffer[3], Level);
audio_keep_flag=true;
}
else{
audio_keep_flag=false;
memset(pLine, 0, 23);
DrawSmallAntennaAndBars(pLine, Level);
}
#endif
if (now)
ST7565_BlitFullScreen();
#endif
@ -295,13 +317,9 @@ void UI_MAIN_TimeSlice500ms(void) {
PrintAGC(true);
return;
#endif
// const bool rx = (gCurrentFunction == FUNCTION_RECEIVE ||
// gCurrentFunction == FUNCTION_MONITOR ||
// gCurrentFunction == FUNCTION_INCOMING);
//
//
// if (rx && mdc1200_rx_ready_tick_500ms <= 0)
// DisplayRSSIBar(true);
if(FUNCTION_IsRx()) {
DisplayRSSIBar(true);
}
}
}
// ***************************************************************************
@ -352,6 +370,7 @@ void UI_DisplayMain(void) {
const bool isMainVFO = (vfo_num == gEeprom.TX_VFO);
uint8_t *p_line0 = gFrameBuffer[line + 0];
uint8_t *p_line1 = gFrameBuffer[line + 1];
enum Vfo_txtr_mode mode = VFO_MODE_NONE;
if (activeTxVFO != vfo_num) // this is not active TX VFO
{
@ -367,48 +386,47 @@ void UI_DisplayMain(void) {
#endif
if (
if (gDTMF_InputMode
#ifdef ENABLE_DTMF_CALLING
gDTMF_CallState != DTMF_CALL_STATE_NONE || gDTMF_IsTx ||
|| gDTMF_CallState != DTMF_CALL_STATE_NONE || gDTMF_IsTx
#endif
gDTMF_InputMode) { // show DTMF stuff
) {
char *pPrintStr = "";
// show DTMF stuff
#ifdef ENABLE_DTMF_CALLING
char Contact[16];
if (!gDTMF_InputMode) {
if (gDTMF_CallState == DTMF_CALL_STATE_CALL_OUT) {
pPrintStr = DTMF_FindContact(gDTMF_String, Contact) ? Contact : gDTMF_String;
} else if (gDTMF_CallState == DTMF_CALL_STATE_RECEIVED || gDTMF_CallState == DTMF_CALL_STATE_RECEIVED_STAY){
pPrintStr = DTMF_FindContact(gDTMF_Callee, Contact) ? Contact : gDTMF_Callee;
}else if (gDTMF_IsTx) {
pPrintStr = gDTMF_String;
}
}
if (!gDTMF_InputMode)
{
memset(Contact, 0, sizeof(Contact));
if (gDTMF_CallState == DTMF_CALL_STATE_CALL_OUT)
strcpy(String, (gDTMF_State == DTMF_STATE_CALL_OUT_RSP) ? "CALL OUT(RSP)" : "CALL OUT");
else
if (gDTMF_CallState == DTMF_CALL_STATE_RECEIVED || gDTMF_CallState == DTMF_CALL_STATE_RECEIVED_STAY)
sprintf(String, "CALL FRM:%s", (DTMF_FindContact(gDTMF_Caller, Contact)) ? Contact : gDTMF_Caller);
else
if (gDTMF_IsTx)
strcpy(String, (gDTMF_State == DTMF_STATE_TX_SUCC) ? "DTMF TX(SUCC)" : "DTMF TX");
UI_PrintStringSmall(pPrintStr, 2, 0, 2 + (vfo_num * 3));
pPrintStr = "";
if (!gDTMF_InputMode) {
if (gDTMF_CallState == DTMF_CALL_STATE_CALL_OUT) {
pPrintStr = (gDTMF_State == DTMF_STATE_CALL_OUT_RSP) ? "CALL OUT(RSP)" : "CALL OUT";
} else if (gDTMF_CallState == DTMF_CALL_STATE_RECEIVED || gDTMF_CallState == DTMF_CALL_STATE_RECEIVED_STAY) {
sprintf(String, "CALL FRM:%s", (DTMF_FindContact(gDTMF_Caller, Contact)) ? Contact : gDTMF_Caller);
pPrintStr = String;
} else if (gDTMF_IsTx) {
pPrintStr = (gDTMF_State == DTMF_STATE_TX_SUCC) ? "DTMF TX(SUCC)" : "DTMF TX";
}
}
else
#endif
{
sprintf(String, ">%s", gDTMF_InputBox);
}
UI_PrintStringSmall(String, 2, 0, 0 + (vfo_num * 3));
#ifdef ENABLE_DTMF_CALLING
memset(String, 0, sizeof(String));
if (!gDTMF_InputMode) {
pPrintStr = String;
memset(Contact, 0, sizeof(Contact));
if (gDTMF_CallState == DTMF_CALL_STATE_CALL_OUT)
sprintf(String, ">%s", (DTMF_FindContact(gDTMF_String, Contact)) ? Contact : gDTMF_String);
else
if (gDTMF_CallState == DTMF_CALL_STATE_RECEIVED || gDTMF_CallState == DTMF_CALL_STATE_RECEIVED_STAY)
sprintf(String, ">%s", (DTMF_FindContact(gDTMF_Callee, Contact)) ? Contact : gDTMF_Callee);
else
if (gDTMF_IsTx)
sprintf(String, ">%s", gDTMF_String);
}
UI_PrintStringSmall(String, 2, 0, 2 + (vfo_num * 3));
#endif
UI_PrintStringSmall(pPrintStr, 2, 0, 0 + (vfo_num * 3));
center_line = CENTER_LINE_IN_USE;
continue;
@ -452,7 +470,7 @@ void UI_DisplayMain(void) {
if (IS_MR_CHANNEL(gEeprom.ScreenChannel[vfo_num])) { // channel mode
const unsigned int x = 2;
const bool inputting = (gInputBoxIndex == 0 || gEeprom.TX_VFO != vfo_num) ? false : true;
const bool inputting = gInputBoxIndex != 0 && gEeprom.TX_VFO == vfo_num;
if (!inputting)
sprintf(String, "M%u", gEeprom.ScreenChannel[vfo_num] + 1);
else
@ -676,8 +694,20 @@ void UI_DisplayMain(void) {
Level = gVFO_RSSI_bar_level[vfo_num];
#endif
}
if (Level)
if (Level) {
#if ENABLE_CHINESE_FULL==0
DrawSmallAntennaAndBars(p_line1 + LCD_WIDTH, Level);
#else
if(IS_MR_CHANNEL(gEeprom.ScreenChannel[vfo_num]) )
{ DrawSmallAntennaAndBars(gFrameBuffer[2]+LCD_WIDTH, Level);
audio_keep_flag=true;
}
else
DrawSmallAntennaAndBars(p_line1 + LCD_WIDTH, Level);
#endif
}
}
// ************
@ -756,7 +786,7 @@ void UI_DisplayMain(void) {
#else
if(IS_MR_CHANNEL(gEeprom.ScreenChannel[vfo_num]) &&!(FUNCTION_IsRx() && gEeprom.RX_VFO == vfo_num ) &&!( gCurrentFunction == FUNCTION_TRANSMIT&&activeTxVFO == vfo_num) )
UI_PrintStringSmall("R", LCD_WIDTH + 24, 0, line - 1);//中文信道1
else if(IS_MR_CHANNEL(gEeprom.ScreenChannel[vfo_num]))
else if(!IS_MR_CHANNEL(gEeprom.ScreenChannel[vfo_num]))
UI_PrintStringSmall("R", LCD_WIDTH + 62, 0, line + 1);//中文信道1
#endif

View File

@ -44,13 +44,13 @@
//}
void UI_DisplayWelcome(void) {
BACKLIGHT_TurnOn();
char WelcomeString0[19] = {0};
char WelcomeString1[19] = {0};
memset(gStatusLine, 0, sizeof(gStatusLine));
memset(gFrameBuffer, 0, sizeof(gFrameBuffer));
BACKLIGHT_TurnOn();
#if ENABLE_CHINESE_FULL == 4

Binary file not shown.

View File

@ -5,9 +5,9 @@
#define VER GIT_HASH
#else
#if ENABLE_CHINESE_FULL ==0
#define VER "111"
#define VER "112"
#else
#define VER "111K"
#define VER "112"
#endif
#endif
@ -16,5 +16,9 @@
const char Version[] = "OEFW-"VER;
const char UART_Version[] = "UV-K5 Firmware, Open Edition, OEFW-"VER"\r\n";
#else
const char Version[] = "LOSEHU"VER;
#if ENABLE_CHINESE_FULL ==0
const char Version[] = "LOSEHU"VER;
#else
const char Version[] = "LOSEHU"VER"K";
#endif
#endif

View File

@ -29,7 +29,7 @@
:: Do the compile
::
make clean
make
:: pyinstaller --onefile ./MDC_WRITE/main.py
:: If you have python installed, you can create a 'packed' .bin from the compiled firmware.bin file.
:: The Quansheng windows upload-to-radio program requires a 'packed' .bin file.