diff -Nru opentx-companion22-2.2.0~ppa02~xenial/CMakeLists.txt opentx-companion22-2.2.1~ppa01~xenial/CMakeLists.txt --- opentx-companion22-2.2.0~ppa02~xenial/CMakeLists.txt 2017-05-31 19:49:19.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/CMakeLists.txt 2017-12-17 16:22:27.000000000 +0000 @@ -2,11 +2,11 @@ set(VERSION_MAJOR "2") set(VERSION_MINOR "2") -set(VERSION_REVISION "0") +set(VERSION_REVISION "1") set(VERSION_SUFFIX $ENV{OPENTX_VERSION_SUFFIX}) set(VERSION_FAMILY ${VERSION_MAJOR}.${VERSION_MINOR}) set(VERSION ${VERSION_MAJOR}.${VERSION_MINOR}.${VERSION_REVISION}${VERSION_SUFFIX}) -set(SDCARD_REVISION "0010") +set(SDCARD_REVISION "0013") set(SDCARD_VERSION ${VERSION_MAJOR}.${VERSION_MINOR}V${SDCARD_REVISION}) cmake_minimum_required(VERSION 2.8) @@ -62,6 +62,16 @@ list(APPEND CMAKE_PREFIX_PATH "${WIN_EXTRA_LIBS_PATH}" "${WIN_EXTRA_LIBS_PATH}/SDL") # hints for FindSDL endif() +# Python check +find_package("PythonInterp") +if(PYTHONINTERP_FOUND) + message(STATUS "Python found, version: ${PYTHON_VERSION_STRING}") + get_filename_component(PYTHON_DIRECTORY ${PYTHON_EXECUTABLE} DIRECTORY) +else() + message(WARNING "Python not found! Most firmware and simu flavors not buildable.") + set(LUA NO) +endif() + find_package(Qt5Core) find_package(Qt5Widgets) find_package(Qt5Xml) diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/appdebugmessagehandler.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/appdebugmessagehandler.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/appdebugmessagehandler.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/appdebugmessagehandler.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -20,6 +20,8 @@ #include "appdebugmessagehandler.h" +#include + AppDebugMessageHandler::AppDebugMessageHandler(QObject * parent) : QObject(parent), m_appDebugOutputLevel(APP_DBG_HANDLER_DEFAULT_LEVEL), @@ -55,6 +57,25 @@ m_showFunctionDeclarations = showFunctionDeclarations; } +void AppDebugMessageHandler::addOutputDevice(QIODevice * device) +{ + if (device && !m_outputDevices.contains(device)) + m_outputDevices.append(device); +} + +void AppDebugMessageHandler::removeOutputDevice(QIODevice * device) +{ + if (device) { + // no QVector::removeAll() in Qt < 5.4 + int i = 0; + foreach (QIODevice * d, m_outputDevices) { + if (d == device) + m_outputDevices.remove(i); + ++i; + } + } +} + void AppDebugMessageHandler::installAppMessageHandler() { m_defaultHandler = qInstallMessageHandler(g_appDebugMessageHandler); @@ -98,7 +119,7 @@ qSetMessagePattern(msgPattern); - if (!m_defaultHandler || receivers(SIGNAL(messageOutput(quint8, const QString &)))) { + if (!m_defaultHandler || m_outputDevices.size() || receivers(SIGNAL(messageOutput(quint8, const QString &)))) { #if (QT_VERSION >= QT_VERSION_CHECK(5, 4, 0)) msgPattern = qFormatLogMessage(type, context, msg); #else @@ -112,6 +133,14 @@ #endif emit messageOutput(lvl, msgPattern); + + foreach (QIODevice * d, m_outputDevices) { + if (d && d->isWritable() && (!d->property("level").isValid() || d->property("level").toInt() <= lvl)) { + d->write(qPrintable(msgPattern % "\n")); + if (QFileDevice * fd = qobject_cast(d)) + fd->flush(); + } + } } // if (QThread::currentThread() == qApp->thread()) // gui thread diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/appdebugmessagehandler.h opentx-companion22-2.2.1~ppa01~xenial/companion/src/appdebugmessagehandler.h --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/appdebugmessagehandler.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/appdebugmessagehandler.h 2017-10-31 16:16:43.000000000 +0000 @@ -26,6 +26,7 @@ #include #include +#include #include #include #include @@ -94,7 +95,7 @@ #else #define qInfo qDebug #endif - #define QtInfoMsg 4 + #define QtInfoMsg QtMsgType(4) #endif class AppDebugMessageHandler : public QObject @@ -110,6 +111,8 @@ void setAppDebugOutputLevel(const quint8 & appDebugOutputLevel); void setShowSourcePath(bool showSourcePath); void setShowFunctionDeclarations(bool showFunctionDeclarations); + void addOutputDevice(QIODevice * device); + void removeOutputDevice(QIODevice * device); void installAppMessageHandler(); void messageHandler(QtMsgType type, const QMessageLogContext & context, const QString & msg); @@ -123,6 +126,7 @@ QRegularExpression m_srcPathFilter; QRegularExpression m_functionFilter; quint8 m_appDebugOutputLevel; + QVector m_outputDevices; bool m_showSourcePath; bool m_showFunctionDeclarations; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/apppreferencesdialog.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/apppreferencesdialog.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/apppreferencesdialog.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/apppreferencesdialog.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -23,13 +23,10 @@ #include "mainwindow.h" #include "appdata.h" #include "helpers.h" -#include "firmwareinterface.h" -#ifdef JOYSTICKS +#if defined(JOYSTICKS) #include "joystick.h" #include "joystickdialog.h" #endif -#include -#include AppPreferencesDialog::AppPreferencesDialog(QWidget * parent) : QDialog(parent), @@ -41,6 +38,8 @@ initSettings(); connect(ui->downloadVerCB, SIGNAL(currentIndexChanged(int)), this, SLOT(baseFirmwareChanged())); + connect(ui->opt_appDebugLog, &QCheckBox::toggled, this, &AppPreferencesDialog::toggleAppLogSettings); + connect(ui->opt_fwTraceLog, &QCheckBox::toggled, this, &AppPreferencesDialog::toggleAppLogSettings); connect(this, SIGNAL(accepted()), this, SLOT(writeValues())); #if !defined(JOYSTICKS) @@ -61,9 +60,8 @@ void AppPreferencesDialog::writeValues() { - g.useCompanionNightlyBuilds(ui->useCompanionNightlyBuilds->isChecked()); g.autoCheckApp(ui->autoCheckCompanion->isChecked()); - g.useFirmwareNightlyBuilds(ui->useFirmwareNightlyBuilds->isChecked()); + g.OpenTxBranch(DownloadBranchType(ui->OpenTxBranch->currentIndex())); g.autoCheckFw(ui->autoCheckFirmware->isChecked()); g.showSplash(ui->showSplash->isChecked()); g.simuSW(ui->simuSW->isChecked()); @@ -77,6 +75,10 @@ g.embedSplashes(ui->splashincludeCB->currentIndex()); g.enableBackup(ui->backupEnable->isChecked()); + g.appDebugLog(ui->opt_appDebugLog->isChecked()); + g.fwTraceLog(ui->opt_fwTraceLog->isChecked()); + g.appLogsDir(ui->appLogsDir->text()); + if (ui->joystickChkB ->isChecked() && ui->joystickCB->isEnabled()) { g.jsSupport(ui->joystickChkB ->isChecked()); g.jsCtrl(ui->joystickCB ->currentIndex()); @@ -131,13 +133,10 @@ ui->snapshotPath->setDisabled(true); ui->snapshotPathButton->setDisabled(true); } -#if defined(ALLOW_NIGHTLY_BUILDS) - ui->useCompanionNightlyBuilds->setChecked(g.useCompanionNightlyBuilds()); - ui->useFirmwareNightlyBuilds->setChecked(g.useFirmwareNightlyBuilds()); -#else - ui->useCompanionNightlyBuilds->hide(); - ui->useFirmwareNightlyBuilds->hide(); +#if !defined(ALLOW_NIGHTLY_BUILDS) + // TODO should we gray out nightly builds here? #endif + ui->OpenTxBranch->setCurrentIndex(g.OpenTxBranch()); ui->autoCheckCompanion->setChecked(g.autoCheckApp()); ui->autoCheckFirmware->setChecked(g.autoCheckFw()); ui->showSplash->setChecked(g.showSplash()); @@ -168,10 +167,15 @@ } } else { - ui->backupEnable->setDisabled(true); + ui->backupEnable->setDisabled(true); } ui->splashincludeCB->setCurrentIndex(g.embedSplashes()); + ui->opt_appDebugLog->setChecked(g.appDebugLog()); + ui->opt_fwTraceLog->setChecked(g.fwTraceLog()); + ui->appLogsDir->setText(g.appLogsDir()); + toggleAppLogSettings(); + #if defined(JOYSTICKS) ui->joystickChkB->setChecked(g.jsSupport()); if (ui->joystickChkB->isChecked()) { @@ -286,6 +290,15 @@ } } + +void AppPreferencesDialog::on_btn_appLogsDir_clicked() +{ + QString fileName = QFileDialog::getExistingDirectory(this, tr("Select a folder for application logs"), ui->appLogsDir->text()); + if (!fileName.isEmpty()) { + ui->appLogsDir->setText(fileName); + } +} + void AppPreferencesDialog::on_ge_pathButton_clicked() { QString fileName = QFileDialog::getOpenFileName(this, tr("Select Google Earth executable"),ui->ge_lineedit->text()); @@ -458,6 +471,14 @@ } } +void AppPreferencesDialog::toggleAppLogSettings() +{ + bool vis = (ui->opt_appDebugLog->isChecked() || ui->opt_fwTraceLog->isChecked()); + ui->appLogsDir->setVisible(vis); + ui->lbl_appLogsDir->setVisible(vis); + ui->btn_appLogsDir->setVisible(vis); +} + void AppPreferencesDialog::populateFirmwareOptions(const Firmware * firmware) { const Firmware * parent = firmware->getFirmwareBase(); @@ -539,4 +560,3 @@ { adjustSize(); } - diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/apppreferencesdialog.h opentx-companion22-2.2.1~ppa01~xenial/companion/src/apppreferencesdialog.h --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/apppreferencesdialog.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/apppreferencesdialog.h 2017-10-31 16:16:43.000000000 +0000 @@ -62,6 +62,7 @@ void shrink(); void baseFirmwareChanged(); void firmwareOptionChanged(bool state); + void toggleAppLogSettings(); void writeValues(); void on_libraryPathButton_clicked(); @@ -74,6 +75,7 @@ void on_sdPathButton_clicked(); void on_SplashSelect_clicked(); void on_clearImageButton_clicked(); + void on_btn_appLogsDir_clicked(); #if defined(JOYSTICKS) void on_joystickChkB_clicked(); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/apppreferencesdialog.ui opentx-companion22-2.2.1~ppa01~xenial/companion/src/apppreferencesdialog.ui --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/apppreferencesdialog.ui 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/apppreferencesdialog.ui 2017-12-17 16:22:27.000000000 +0000 @@ -6,8 +6,8 @@ 0 0 - 623 - 537 + 863 + 673 @@ -26,9 +26,6 @@ true - - 6 - @@ -763,350 +760,471 @@ Application Settings - - - - - - 0 - 0 - - - - Automatic Backup Folder - - - - - - - Automatic check for Companion updates - - - true - - - - - - - Show splash screen when Companion starts - - - true - - - - - - - - 40 - 0 - - - - - 50 - 16777215 - - - - 50 - - - 10 - - - - - - - Use OpenTX firmware nightly builds - - - false - - - - - - - - 350 - 0 - - - - false - - - - - - - - 0 - 0 - - - - - Only show user splash images - + + + + + 6 + + + + + + + Automatic check for OpenTX firmware updates + + + true + + + + + + + Automatic check for Companion updates + + + true + + + + + + + + 0 + 0 + + + + + Use releases (stable) + + + + + Use releases and release candidates (testing) + + + + + Use nightly builds (unstable) + + + + + + + + + + 6 + + + + + + 40 + 0 + + + + 50 + + + 10 + + + + + + + + 0 + 0 + + + + most recently used files + + + + - - - Show user and companion splash images - + + + + + 0 + 0 + + + + Startup Settings + + - - - - - - Qt::Horizontal - - - - - - - - 0 - 0 - - - - Files to keep - - - - - - - Qt::Horizontal - - - - - - - Qt::Horizontal - - - - - - - Automatic check for OpenTX firmware updates - - - true - - - - - - - - 0 - 0 - - - - Select Folder - - - - - - - - 0 - 0 - - - - Splash Screen Library - - - - - - - - 0 - 0 - - - - Google Earth Executable - - - - - - - Qt::Vertical - - - - 20 - 5 - - - - - - - - - 0 - 0 - - - - Enable automatic backup before writing firmware - - - - - - - true - - - false - - - - - - - Qt::Horizontal - - - - - - - - 0 - 0 - - - - User Splash Screens - - - - - - - Use Companion nightly builds - - - false - - - - - - - - 350 - 0 - - - - true - - - - - - - - 0 - 0 - - - - Select Executable - - - - - - - - 0 - 0 - - - - Select Folder - - - - - - - - 0 - 0 - - - - Action on New Model - - - - - - - <html><head/><body><p>This option maintains the behaviour from older OpenTx versions where empty model slots are preserved when a model is deleted or moved. </p><p>When this option is de-selected, the other models may be re-arranged to fill the gap left by the removed model.</p></body></html> - - - Remove empty model slots when deleting models (only applies for radios w/out categories) - - - - - - - + + + + + 0 + 0 + + - Use model wizard + Google Earth Executable - - btnGrp_newModelActions - - - + + + + + 0 + 0 + + - Open model editor + Automatic Backup Folder - - btnGrp_newModelActions - - - + + + + Qt::Horizontal + + + + + + + + 0 + 0 + + - Just create the model + Remember + + + + + + + Show splash screen when Companion starts + + + true + + + + + + + + + false + + + + + + + + 0 + 0 + + + + Select Folder + + + + + + + + + + + true + + + false + + + + + + + + 0 + 0 + + + + Select Folder + + + + + + + + + + 0 + 0 + + + + Output Logs Folder + + + + + + + Qt::Horizontal + + + + + + + <html><head/><body><p>This option maintains the behaviour from older OpenTx versions where empty model slots are preserved when a model is deleted or moved. </p><p>When this option is de-selected, the other models may be re-arranged to fill the gap left by the removed model.</p></body></html> + + + Remove empty model slots when deleting models (only applies for radios w/out categories) + + + + + + + + + Use model wizard + + + btnGrp_newModelActions + + + + + + + Open model editor + + + btnGrp_newModelActions + + + + + + + Just create the model + + + btnGrp_newModelActions + + + + + + + + + + 0 + 0 + + + + Enable automatic backup before writing firmware + + + + + + + + 0 + 0 + + + + Debug Output Logging + + + + + + + Qt::Horizontal + + + + + + + + 0 + 0 + + + + + Only show user splash images + + + + + Show user and companion splash images + + + + + + + + Qt::Horizontal + + + + + + + + + true + + + + + + + + 0 + 0 + + + + Select Executable + + + + + + + + + + + true + + + false + + + + + + + Select Folder + + + + + + + + + + + <html><head/><body><p>Keep a log of all debugging messages generated by the desktop Companion/Simulator applications. An OpenTX developer may request this to help diagnose an issue.</p></body></html> + + + Application (Companion/Simulator) + + + + + + + <html><head/><body><p>Keep a log of all messages generated by the radio firmware when running in Simulator. This is the same information one would also see in the Simulator <span style=" font-style:italic;">Debug Output</span> window.</p></body></html> + + + Radio Firmware (in Simulator) + + + + + + + + + + 0 + 0 + + + + Splash Screen Library + + + + + + + Qt::Horizontal + + + + + + + + 0 + 0 + + + + User Splash Screens + + + + + + + + 0 + 0 + + + + Action on New Model - - btnGrp_newModelActions - + + + + Qt::Vertical + + + + 20 + 5 + + + + @@ -1181,7 +1299,7 @@ - Simulator capture folder + Screenshot capture folder @@ -1363,18 +1481,7 @@ channelorderCB renameFirmware burnFirmware - ge_lineedit - ge_pathButton - historySize - showSplash - autoCheckFirmware - autoCheckCompanion - backupPath - backupPathButton - backupEnable splashincludeCB - libraryPath - libraryPathButton snapshotPath snapshotPathButton snapshotClipboardCKB diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/boards.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/boards.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/boards.cpp 2017-04-29 16:57:04.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/boards.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -99,6 +99,7 @@ case BOARD_TARANIS_X9D: case BOARD_TARANIS_X9DP: case BOARD_TARANIS_X9E: + case BOARD_TARANIS_X7: case BOARD_FLAMENCO: return FSIZE_TARANIS; case BOARD_X12S: @@ -151,10 +152,10 @@ } else { const Board::SwitchInfo switches[] = { + {SWITCH_3POS, "3POS"}, {SWITCH_2POS, "THR"}, {SWITCH_2POS, "RUD"}, {SWITCH_2POS, "ELE"}, - {SWITCH_3POS, "3POS"}, {SWITCH_2POS, "AIL"}, {SWITCH_2POS, "GEA"}, {SWITCH_TOGGLE, "TRN"} @@ -171,37 +172,29 @@ switch (capability) { case Sticks: return 4; + case Pots: - if (IS_HORUS(board)) - return 3; - else if (IS_TARANIS_X7(board)) + if (IS_TARANIS_X7(board)) return 2; else if (IS_TARANIS_X9E(board)) return 4; - else if (IS_TARANIS(board)) - return 3; else return 3; + case Sliders: - if (IS_HORUS(board)) + if (IS_HORUS_X12S(board) || IS_TARANIS_X9E(board)) return 4; - else if (IS_TARANIS_X7(board)) - return 0; - else if (IS_TARANIS_X9E(board)) - return 4; - else if (IS_TARANIS(board)) + else if (IS_TARANIS_X9D(board) || IS_HORUS_X10(board)) return 2; else return 0; + case MouseAnalogs: - if (IS_HORUS(board)) + if (IS_HORUS_X12S(board)) return 2; else return 0; - case FactoryInstalledSwitches: - if (IS_TARANIS_X9E(board)) - return 8; - // no break + case Switches: if (IS_TARANIS_X9E(board)) return 18; @@ -211,16 +204,25 @@ return 8; else return 7; + + case FactoryInstalledSwitches: + if (IS_TARANIS_X9E(board)) + return 8; + else + return getCapability(board, Switches); + case SwitchPositions: if (IS_HORUS_OR_TARANIS(board)) return getCapability(board, Switches) * 3; else return 9; + case NumTrims: if (IS_HORUS(board)) return 6; else return 4; + case NumTrimSwitches: return getCapability(board, NumTrims) * 2; } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/burnconfigdialog.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/burnconfigdialog.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/burnconfigdialog.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/burnconfigdialog.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -105,6 +105,18 @@ delete ui; } +QStringList burnConfigDialog::getAvrdudeArgs() +{ + QStringList args = avrArgs; + if (!avrPort.isEmpty()) + args << "-P" << avrPort; + +#if defined(__APPLE__) + args << "-C" << QFileInfo(QApplication::applicationDirPath() + "/../Resources/avrdude.conf").absoluteFilePath(); +#endif + return args; +} + void burnConfigDialog::getSettings() { avrLoc = g.avrdudeLocation(); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/burnconfigdialog.h opentx-companion22-2.2.1~ppa01~xenial/companion/src/burnconfigdialog.h --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/burnconfigdialog.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/burnconfigdialog.h 2017-10-31 16:16:43.000000000 +0000 @@ -42,7 +42,7 @@ QString getAVRDUDE() {return avrLoc;} QString getSAMBA() {return sambaLoc;} QString getDFU() {return dfuLoc;} - QStringList getAvrdudeArgs() { QStringList args = avrArgs; if (!avrPort.isEmpty()) args << "-P" << avrPort; return args; } + QStringList getAvrdudeArgs(); QStringList getDFUArgs() {return dfuArgs;} QString getProgrammer() {return avrProgrammer;} QString getMCU() {return avrMCU;} diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/CMakeLists.txt opentx-companion22-2.2.1~ppa01~xenial/companion/src/CMakeLists.txt --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/CMakeLists.txt 2017-05-14 17:18:57.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/CMakeLists.txt 2017-10-31 16:16:43.000000000 +0000 @@ -25,6 +25,7 @@ # the binary (default homebrew path) set(DFU_UTIL_PATH "/usr/local/bin/dfu-util") set(AVRDUDE_PATH "/usr/local/bin/avrdude") +set(AVRDUDE_CONF "/usr/local/etc/avrdude.conf") option(ALLOW_NIGHTLY_BUILDS "Allow nightly builds download / update") # Disabled by default if(ALLOW_NIGHTLY_BUILDS) @@ -350,6 +351,7 @@ install(FILES images/linuxicons/512x512/companion.png DESTINATION ${INSTALL_TEMP_SHR_PFX}share/icons/hicolor/512x512/apps RENAME companion${C9X_NAME_SUFFIX}.png) install(FILES images/linuxicons/scalable/companion.svg DESTINATION ${INSTALL_TEMP_SHR_PFX}share/icons/hicolor/scalable/apps RENAME companion${C9X_NAME_SUFFIX}.svg) install(FILES ../targets/linux/45-companion-taranis.rules DESTINATION ${INSTALL_TEMP_LIB_PFX}lib/udev/rules.d RENAME 45-companion${C9X_NAME_SUFFIX}-taranis.rules) + install(FILES ../targets/linux/45-usbasp.rules DESTINATION ${INSTALL_TEMP_LIB_PFX}lib/udev/rules.d RENAME 45-companion${C9X_NAME_SUFFIX}-usbasp.rules) # Linux specific code set(OperatingSystem "Linux") @@ -523,8 +525,12 @@ # Copy dfu-util and avrdude, resolve symlink first get_filename_component(DFU_UTIL_ABSOLUTE_PATH ${DFU_UTIL_PATH} REALPATH) get_filename_component(AVRDUDE_ABSOLUTE_PATH ${AVRDUDE_PATH} REALPATH) + get_filename_component(AVRDUDECONF_ABSOLUTE_PATH ${AVRDUDE_CONF} REALPATH) install(PROGRAMS ${DFU_UTIL_ABSOLUTE_PATH} ${AVRDUDE_ABSOLUTE_PATH} DESTINATION ${companion_res_dir} COMPONENT Runtime) + install(FILES ${AVRDUDECONF_ABSOLUTE_PATH} DESTINATION ${companion_res_dir} COMPONENT Runtime) + set(bundle_tools_path "\${CMAKE_INSTALL_PREFIX}/${companion_res_dir}/dfu-util;\${CMAKE_INSTALL_PREFIX}/${companion_res_dir}/avrdude") + # Include depencies (adding frameworks, fixing the embbeded libraries) # I get write errors without setting BU_CHMOD_BUNDLE_ITEMS even though it is @@ -553,6 +559,7 @@ set(CPACK_DEBIAN_PACKAGE_VERSION_MAJOR ${VERSION_MAJOR}) set(CPACK_DEBIAN_PACKAGE_VERSION_MINOR ${VERSION_MINOR}) set(CPACK_DEBIAN_ARCHITECTURE $(CMAKE_SYSTEM_PROCESSOR)) + set(CPACK_DEBIAN_PACKAGE_DEPENDS "libqt5multimedia5-plugins") set(CPACK_DEBIAN_PACKAGE_SHLIBDEPS ON) elseif(APPLE) set(CPACK_GENERATOR "DragNDrop") diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/companion.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/companion.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/companion.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/companion.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -19,6 +19,9 @@ */ #include +#include +#include +#include #include #if defined(JOYSTICKS) || defined(SIMU_AUDIO) #include @@ -68,6 +71,20 @@ CustomDebug::setFilterRules(); + if (!g.hasCurrentSettings()) { + QString previousVersion; + if (g.findPreviousVersionSettings(&previousVersion)) { + QMessageBox msgBox; + msgBox.setText(QObject::tr("We have found existing settings for Companion version: %1.\nDo you want to import them?").arg(previousVersion)); + msgBox.setIcon(QMessageBox::Information); + msgBox.setStandardButtons(QMessageBox::Yes | QMessageBox::No); + msgBox.setDefaultButton(QMessageBox::Yes); + int ret = msgBox.exec(); + + if (ret == QMessageBox::Yes) + g.importSettings(previousVersion); + } + } g.init(); QStringList strl = QApplication::arguments(); @@ -77,14 +94,21 @@ exit(0); } + QFile dbgLog; + if (AppDebugMessageHandler::instance() && g.appDebugLog() && !g.appLogsDir().isEmpty() && QDir().mkpath(g.appLogsDir())) { + QString fn = g.appLogsDir() % "/CompanionDebug_" % QDateTime::currentDateTime().toString("yy-MM-dd_HH-mm-ss") % ".log"; + dbgLog.setFileName(fn); + if (dbgLog.open(QIODevice::WriteOnly | QIODevice::Text)) { + AppDebugMessageHandler::instance()->addOutputDevice(&dbgLog); + } + } + #ifdef __APPLE__ app.setStyle(new MyProxyStyle); #endif Translations::installTranslators(); - // QTextCodec::setCodecForCStrings(QTextCodec::codecForName("UTF-8")); - #if defined(JOYSTICKS) || defined(SIMU_AUDIO) uint32_t sdlFlags = 0; #ifdef JOYSTICKS @@ -139,5 +163,11 @@ #endif qDebug() << "COMPANION EXIT" << result; + + if (dbgLog.isOpen()) { + AppDebugMessageHandler::instance()->removeOutputDevice(&dbgLog); + dbgLog.close(); + } + return result; } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/companion.qrc opentx-companion22-2.2.1~ppa01~xenial/companion/src/companion.qrc --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/companion.qrc 2017-05-14 17:18:57.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/companion.qrc 2017-11-20 18:44:06.000000000 +0000 @@ -47,21 +47,32 @@ images/simulator/icons/svg/trainer-active.svg images/simulator/icons/svg/word_wrap.svg images/simulator/icons/svg/word_wrap-on.svg - images/simulator/Horus/middle.png - images/simulator/Horus/left.png - images/simulator/Horus/right.png - images/simulator/Horus/top.png - images/simulator/Horus/bottom.png - images/simulator/Horus/led.png - images/simulator/Horus/border-right.png - images/simulator/Horus/left_btn1.png - images/simulator/Horus/left_btn2.png - images/simulator/Horus/left_scrnsht.png - images/simulator/Horus/right_btnU.png - images/simulator/Horus/right_btnL.png - images/simulator/Horus/right_btnD.png - images/simulator/Horus/right_btnR.png - images/simulator/Horus/right_ent.png + images/simulator/X12/middle.png + images/simulator/X12/left.png + images/simulator/X12/right.png + images/simulator/X12/top.png + images/simulator/X12/bottom.png + images/simulator/X12/led.png + images/simulator/X12/border-right.png + images/simulator/X12/left_btn1.png + images/simulator/X12/left_btn2.png + images/simulator/X12/left_scrnsht.png + images/simulator/X12/right_btnU.png + images/simulator/X12/right_btnL.png + images/simulator/X12/right_btnD.png + images/simulator/X12/right_btnR.png + images/simulator/X12/right_ent.png + images/simulator/X10/left.png + images/simulator/X10/right.png + images/simulator/X10/top.png + images/simulator/X10/bottom.png + images/simulator/X10/left_mdl.png + images/simulator/X10/left_page.png + images/simulator/X10/left_scrnsht.png + images/simulator/X10/left_rtn.png + images/simulator/X10/left_sys.png + images/simulator/X10/left_tele.png + images/simulator/X10/right_ent.png images/simulator/9X/9xdb.png images/simulator/9X/9xdl.png images/simulator/9X/9xdr.png diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/constants.h opentx-companion22-2.2.1~ppa01~xenial/companion/src/constants.h --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/constants.h 2017-05-14 17:18:57.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/constants.h 2017-12-17 16:22:27.000000000 +0000 @@ -68,4 +68,12 @@ #define CPN_STR_SW_INDICATOR_NEUT QCoreApplication::translate("RawSwitch", "-") // Switch neutral (middle) position indicator. #define CPN_STR_SW_INDICATOR_REV QCoreApplication::translate("RawSwitch", "!") // Switch reversed logic (NOT) indicator. +enum DownloadBranchType { + BRANCH_RELEASE_STABLE, + BRANCH_RC_TESTING, + BRANCH_NIGHTLY_UNSTABLE +}; + +Q_DECLARE_METATYPE(DownloadBranchType) + #endif // _CONSTANTS_H_ diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/eeprominterface.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/eeprominterface.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/eeprominterface.cpp 2017-05-31 19:49:19.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/eeprominterface.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -114,6 +114,23 @@ } } +QString getElementName(const QString & prefix, unsigned int index, const char * name = NULL, bool padding = false) +{ + QString result = prefix; + if (padding) + result += QString("%1").arg(index, 2, 10, QChar('0')); + else + result += QString("%1").arg(index); + if (name) { + QString trimmed = QString(name).trimmed(); + if (trimmed.length() > 0) { + result += ":" + QString(name).trimmed(); + } + } + return result; +} + + float ValToTim(int value) { return ((value < -109 ? 129+value : (value < 7 ? (113+value)*5 : (53+value)*10))/10.0); @@ -508,10 +525,12 @@ int genAryIdx = 0; switch (type) { case SOURCE_TYPE_VIRTUAL_INPUT: - result = QObject::tr("[I%1]").arg(index+1, 2, 10, QChar('0')); - if (model && model->inputNames[index][0]) - result.append(/*":" + */QString(model->inputNames[index]).trimmed()); - return result; + { + const char * name = NULL; + if (model) + name = model->inputNames[index]; + return getElementName(QCoreApplication::translate("Input", "I"), index + 1, name); + } case SOURCE_TYPE_LUA_OUTPUT: return QObject::tr("LUA%1%2").arg(index/16+1).arg(QChar('a'+index%16)); @@ -550,13 +569,15 @@ return QObject::tr("CYC%1").arg(index+1); case SOURCE_TYPE_PPM: - return QObject::tr("TR%1").arg(index+1, 2, 10, QChar('0')); + return getElementName(QCoreApplication::translate("Trainer", "TR"), index + 1); case SOURCE_TYPE_CH: - result = QObject::tr("CH%1").arg(index+1, 2, 10, QChar('0')); - if (getCurrentFirmware()->getCapability(ChannelsName) && model && model->limitData[index].name[0]) - result.append(":" + QString(model->limitData[index].name).trimmed()); - return result; + { + const char * name = NULL; + if (getCurrentFirmware()->getCapability(ChannelsName) && model) + name = model->limitData[index].name; + return getElementName(QCoreApplication::translate("Channel", "CH"), index + 1, name); + } case SOURCE_TYPE_SPECIAL: return CHECK_IN_ARRAY(special, index); @@ -564,7 +585,7 @@ case SOURCE_TYPE_TELEMETRY: if (IS_ARM(getCurrentBoard())) { div_t qr = div(index, 3); - result = model ? QString(model->sensorData[qr.quot].label) : QString("[T%1]").arg(qr.quot+1, 2, 10, QChar('0')); + result = getElementName(QCoreApplication::translate("Telemetry", "TELE"), qr.quot+1, model ? model->sensorData[qr.quot].label : NULL); if (qr.rem) result += (qr.rem == 1 ? "-" : "+"); return result; @@ -574,10 +595,12 @@ } case SOURCE_TYPE_GVAR: - result = QObject::tr("GV%1").arg(index+1, 2, 10, QChar('0')); - if (getCurrentFirmware()->getCapability(GvarsName) && model && model->gvars_names[index][0]) - result.append(":" + QString(model->gvars_names[index]).trimmed()); - return result; + { + const char * name = NULL; + if (getCurrentFirmware()->getCapability(GvarsName) && model) + name = model->gvarData[index].name; + return getElementName(QCoreApplication::translate("Global Variable", "GV"), index + 1, name); + } default: return QObject::tr("----"); @@ -622,7 +645,7 @@ * RawSwitch */ -QString RawSwitch::toString(Board::Type board, const GeneralSettings * const generalSettings) const +QString RawSwitch::toString(Board::Type board, const GeneralSettings * const generalSettings, const ModelData * const modelData) const { if (board == Board::BOARD_UNKNOWN) { board = getCurrentBoard(); @@ -634,10 +657,6 @@ QString("AIL"), QString("GEA"), QString("TRN") }; - static const QString flightModes[] = { - QObject::tr("FM0"), QObject::tr("FM1"), QObject::tr("FM2"), QObject::tr("FM3"), QObject::tr("FM4"), QObject::tr("FM5"), QObject::tr("FM6"), QObject::tr("FM7"), QObject::tr("FM8") - }; - static const QString trimsSwitches[] = { QObject::tr("RudTrim Left"), QObject::tr("RudTrim Right"), QObject::tr("EleTrim Down"), QObject::tr("EleTrim Up"), @@ -662,7 +681,7 @@ << CPN_STR_SW_INDICATOR_DN; if (index < 0) { - return CPN_STR_SW_INDICATOR_REV % RawSwitch(type, -index).toString(board, generalSettings); + return CPN_STR_SW_INDICATOR_REV % RawSwitch(type, -index).toString(board, generalSettings, modelData); } else { QString swName; @@ -682,7 +701,7 @@ } case SWITCH_TYPE_VIRTUAL: - return QObject::tr("L%1").arg(index, 2, 10, QChar('0')); + return getElementName(QCoreApplication::translate("Logic Switch", "L"), index, NULL, true); case SWITCH_TYPE_MULTIPOS_POT: if (!getCurrentFirmware()->getCapability(MultiposPotsPositions)) @@ -710,7 +729,7 @@ return QObject::tr("One"); case SWITCH_TYPE_FLIGHT_MODE: - return CHECK_IN_ARRAY(flightModes, index-1); + return getElementName(QCoreApplication::translate("Flight mode", "FM"), index - 1, modelData ? modelData->flightModeData[index-1].name : NULL); case SWITCH_TYPE_NONE: return QObject::tr("----"); @@ -718,6 +737,12 @@ case SWITCH_TYPE_TIMER_MODE: return CHECK_IN_ARRAY(timerModes, index); + case SWITCH_TYPE_SENSOR: + return getElementName(QCoreApplication::translate("Telemetry", "TELE"), index, modelData ? modelData->sensorData[index-1].label : NULL); + + case SWITCH_TYPE_TELEMETRY: + return QObject::tr("Telemetry"); + default: return QObject::tr("???"); } @@ -1086,10 +1111,7 @@ QString CurveData::nameToString(const int idx) const { - QString ret = QCoreApplication::translate("CurveData", "CV%1").arg(idx+1, 2, 10, QChar('0')); - if (name[0]) - ret.append(":" + QString(name).trimmed()); - return ret; + return getElementName(QCoreApplication::translate("Curve", "CV"), idx + 1, name); } QString LimitData::minToString() const @@ -1156,7 +1178,6 @@ memset(this, 0, sizeof(GeneralSettings)); contrast = 25; - vBatWarn = 90; for (int i=0; i < CPN_MAX_ANALOGS; ++i) { calibMid[i] = 0x200; @@ -1167,7 +1188,29 @@ Firmware * firmware = Firmware::getCurrentVariant(); Board::Type board = firmware->getBoard(); - for (int i=0; i1024 && iGVAR_MAX_VALUE && i= phaseIdx) nextPhase += 1; phaseIdx = nextPhase; idx = flightModeData[phaseIdx].gvars[gvarIdx]; @@ -1746,6 +1791,29 @@ return 100; } +bool ModelData::isAvailable(const RawSwitch & swtch) const +{ + unsigned index = abs(swtch.index) - 1; + + if (swtch.type == SWITCH_TYPE_VIRTUAL) { + return logicalSw[index].func != LS_FN_OFF; + } + else if (swtch.type == SWITCH_TYPE_FLIGHT_MODE) { + return index == 0 || flightModeData[index].swtch.type != SWITCH_TYPE_NONE; + } + else if (swtch.type == SWITCH_TYPE_SENSOR) { + return strlen(sensorData[index].label) > 0; + } + else { + return true; + } +} + +float ModelData::getGVarFieldValuePrec(int phaseIdx, int gvarIdx) +{ + return getGVarFieldValue(phaseIdx, gvarIdx) * gvarData[gvarIdx].multiplierGet(); +} + QList eepromInterfaces; void unregisterEEpromInterfaces() @@ -1797,7 +1865,7 @@ std::bitset errors((unsigned long long)errorsFound); QStringList warningsList; if (errors.test(WARNING_WRONG_FIRMWARE)) { warningsList << QT_TRANSLATE_NOOP("EepromInterface", "- Your radio probably uses a wrong firmware,\n eeprom size is 4096 but only the first 2048 are used"); } - if (errors.test(OLD_VERSION)) { warningsList << QT_TRANSLATE_NOOP("EepromInterface", "- Your eeprom is from an old version of OpenTX, upgrading!\n You should 'save as' to keep the old file as a backup."); } + if (errors.test(OLD_VERSION)) { warningsList << QT_TRANSLATE_NOOP("EepromInterface", "- Your eeprom is from an old version of OpenTX, upgrading!\n To keep your original file as a backup, please choose File -> Save As specifying a different name."); } QMessageBox msgBox(parent); msgBox.setWindowTitle(title); @@ -1880,3 +1948,67 @@ } } } + +QString GVarData::unitToString() const +{ + switch (unit) { + case GVAR_UNIT_NUMBER: + return QObject::tr(""); + case GVAR_UNIT_PERCENT: + return QObject::tr("%"); + default: + return QObject::tr("?"); // highlight unknown value + } +} + +QString GVarData::precToString() const +{ + switch (prec) { + case GVAR_PREC_MUL10: + return QObject::tr("0._"); + case GVAR_PREC_MUL1: + return QObject::tr("0.0"); + default: + return QObject::tr("?.?"); // highlight unknown value + } +} + +int GVarData::multiplierSet() +{ + return (prec == 0 ? 1 : 10); +} + +float GVarData::multiplierGet() const +{ + return (prec == 0 ? 1 : 0.1); +} + +void GVarData::setMin(float val) +{ + min = (val * multiplierSet()) - GVAR_MIN_VALUE; +} + +void GVarData::setMax(float val) +{ + max = GVAR_MAX_VALUE - (val * multiplierSet()); +} + +int GVarData::getMin() const +{ + return GVAR_MIN_VALUE + min; +} + +int GVarData::getMax() const +{ + return GVAR_MAX_VALUE - max; +} + +float GVarData::getMinPrec() const +{ + return getMin() * multiplierGet(); +} + +float GVarData::getMaxPrec() const +{ + return getMax() * multiplierGet(); +} diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/eeprominterface.h opentx-companion22-2.2.1~ppa01~xenial/companion/src/eeprominterface.h --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/eeprominterface.h 2017-04-29 16:57:04.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/eeprominterface.h 2017-12-17 16:22:27.000000000 +0000 @@ -69,6 +69,8 @@ SoundMod, SoundPitch, MaxVolume, + MaxContrast, + MinContrast, Haptic, HasBeeper, ModelTrainerEnable, diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/firmwares/er9x/er9xeeprom.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/firmwares/er9x/er9xeeprom.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/firmwares/er9x/er9xeeprom.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/firmwares/er9x/er9xeeprom.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -95,7 +95,6 @@ result.view = std::min((uint8_t)4, view); result.disableThrottleWarning = disableThrottleWarning; - result.switchWarning = disableSwitchWarning ? 0 : -1; result.disableMemoryWarning = disableMemoryWarning; switch (beeperVal) { diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/firmwares/er9x/er9xinterface.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/firmwares/er9x/er9xinterface.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/firmwares/er9x/er9xinterface.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/firmwares/er9x/er9xinterface.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -82,7 +82,9 @@ #if 0 unsigned long Er9xInterface::loadxml(RadioData &radioData, QDomDocument &doc) { - std::cout << "trying er9x xml import... "; + QDebug dbg = qDebug(); + dbg.setAutoInsertSpaces(false); + dbg << "trying er9x xml import... "; std::bitset errors; @@ -94,7 +96,7 @@ } else { radioData.generalSettings=er9xGeneral; - std::cout << "version " << (unsigned int)er9xGeneral.myVers << " "; + dbg << "version " << (unsigned int)er9xGeneral.myVers << " "; } for (int i=0; i errors; if (size != Boards::getEEpromSize(Board::BOARD_STOCK)) { - std::cout << "wrong size\n"; + dbg << "wrong size"; errors.set(WRONG_SIZE); return errors.to_ulong(); } if (!efile->EeFsOpen((uint8_t *)eeprom, size, Board::BOARD_STOCK)) { - std::cout << "wrong file system\n"; + dbg << "wrong file system"; errors.set(WRONG_FILE_SYSTEM); return errors.to_ulong(); } @@ -132,16 +136,16 @@ Er9xGeneral er9xGeneral; if (efile->readRlc1((uint8_t*)&er9xGeneral, 1) != 1) { - std::cout << "no\n"; + dbg << "no"; errors.set(UNKNOWN_ERROR); return errors.to_ulong(); } - std::cout << "version " << (unsigned int)er9xGeneral.myVers << " "; + dbg << "version " << (unsigned int)er9xGeneral.myVers << " "; switch(er9xGeneral.myVers) { case 3: - std::cout << "(old gruvin9x) "; + dbg << "(old gruvin9x) "; case 4: // case 5: case 6: @@ -151,14 +155,14 @@ case 10: break; default: - std::cout << "not er9x\n"; + dbg << "not er9x"; errors.set(NOT_ER9X); return errors.to_ulong(); } efile->openRd(FILE_GENERAL); if (!efile->readRlc1((uint8_t*)&er9xGeneral, sizeof(Er9xGeneral))) { - std::cout << "ko\n"; + dbg << "ko"; errors.set(UNKNOWN_ERROR); return errors.to_ulong(); @@ -177,7 +181,7 @@ } } - std::cout << "ok\n"; + dbg << "ok"; errors.set(ALL_OK); return errors.to_ulong(); } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/firmwares/ersky9x/ersky9xeeprom.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/firmwares/ersky9x/ersky9xeeprom.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/firmwares/ersky9x/ersky9xeeprom.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/firmwares/ersky9x/ersky9xeeprom.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -120,7 +120,6 @@ result.trainer = trainer; result.view = std::min((uint8_t)4, view); result.disableThrottleWarning = disableThrottleWarning; - result.switchWarning = disableSwitchWarning ? 0 : -1; result.disableMemoryWarning = disableMemoryWarning; switch (beeperVal) { diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/firmwares/ersky9x/ersky9xinterface.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/firmwares/ersky9x/ersky9xinterface.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/firmwares/ersky9x/ersky9xinterface.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/firmwares/ersky9x/ersky9xinterface.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -116,7 +116,9 @@ #if 0 unsigned long Ersky9xInterface::loadxml(RadioData &radioData, QDomDocument &doc) { - std::cout << "trying ersky9x xml import... "; + QDebug dbg = qDebug(); + dbg.setAutoInsertSpaces(false); + dbg << "trying ersky9x xml import... "; std::bitset errors; @@ -128,25 +130,25 @@ } else { radioData.generalSettings=ersky9xGeneral; - std::cout << "version " << (unsigned int)ersky9xGeneral.myVers << " "; + dbg << "version " << (unsigned int)ersky9xGeneral.myVers << " "; } for(int i=0; i(&doc, &radioData.models[i], i, radioData.generalSettings.stickMode+1)) { - std::cout << "ko\n"; + dbg << "ko"; errors.set(UNKNOWN_ERROR); return errors.to_ulong(); } } else { if (!loadModelDataXML(&doc, &radioData.models[i], i, radioData.generalSettings.stickMode+1)) { - std::cout << "ko\n"; + dbg << "ko"; errors.set(UNKNOWN_ERROR); return errors.to_ulong(); } } } - std::cout << "ok\n"; + dbg << "ok"; errors.set(ALL_OK); return errors.to_ulong(); } @@ -154,18 +156,20 @@ unsigned long Ersky9xInterface::load(RadioData &radioData, const uint8_t *eeprom, int size) { - std::cout << "trying ersky9x import... "; + QDebug dbg = qDebug(); + dbg.setAutoInsertSpaces(false); + dbg << "trying ersky9x import... "; std::bitset errors; if (size != Boards::getEEpromSize(Board::BOARD_SKY9X)) { - std::cout << "wrong size\n"; + dbg << "wrong size"; errors.set(WRONG_SIZE); return errors.to_ulong(); } if (!efile->EeFsOpen((uint8_t *)eeprom, size, Board::BOARD_SKY9X)) { - std::cout << "wrong file system\n"; + dbg << "wrong file system"; errors.set(WRONG_FILE_SYSTEM); return errors.to_ulong(); } @@ -174,12 +178,12 @@ Ersky9xGeneral ersky9xGeneral; if (efile->readRlc2((uint8_t*)&ersky9xGeneral, 1) != 1) { - std::cout << "no\n"; + dbg << "no"; errors.set(UNKNOWN_ERROR); return errors.to_ulong(); } - std::cout << "version " << (unsigned int)ersky9xGeneral.myVers << " "; + dbg << "version " << (unsigned int)ersky9xGeneral.myVers << " "; switch(ersky9xGeneral.myVers) { case 10: @@ -187,13 +191,13 @@ case 11: break; default: - std::cout << "not ersky9x\n"; + dbg << "not ersky9x"; errors.set(NOT_ERSKY9X); return errors.to_ulong(); } efile->openRd(FILE_GENERAL); if (!efile->readRlc2((uint8_t*)&ersky9xGeneral, sizeof(Ersky9xGeneral))) { - std::cout << "ko\n"; + dbg << "ko"; errors.set(UNKNOWN_ERROR); return errors.to_ulong(); } @@ -225,7 +229,7 @@ } } - std::cout << "ok\n"; + dbg << "ok"; errors.set(ALL_OK); return errors.to_ulong(); } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/firmwares/opentx/opentxeeprom.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/firmwares/opentx/opentxeeprom.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/firmwares/opentx/opentxeeprom.cpp 2017-05-31 19:49:19.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/firmwares/opentx/opentxeeprom.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -133,6 +133,7 @@ addConversion(RawSwitch(SWITCH_TYPE_OFF), -val+offset); addConversion(RawSwitch(SWITCH_TYPE_ON), val++); + if (version >= 216) { addConversion(RawSwitch(SWITCH_TYPE_ONE, -1), -val+offset); addConversion(RawSwitch(SWITCH_TYPE_ONE, 1), val++); @@ -144,6 +145,15 @@ } } + if (IS_ARM(board) && version >= 218) { + addConversion(RawSwitch(SWITCH_TYPE_TELEMETRY, -1), -val+offset); + addConversion(RawSwitch(SWITCH_TYPE_TELEMETRY, 1), val++); + for (int i=1; i<=CPN_MAX_SENSORS; i++) { + addConversion(RawSwitch(SWITCH_TYPE_SENSOR, -i), -val+offset); + addConversion(RawSwitch(SWITCH_TYPE_SENSOR, i), val++); + } + } + if (version < 216) { // previous "moment" switches for (int i=1; i<=MAX_SWITCHES_POSITION(board, version); i++) { @@ -616,7 +626,7 @@ }; -int smallGvarToEEPROM(int gvar) +int smallGvarImport(int gvar) { if (gvar < -10000) { gvar = 128 + gvar + 10000; @@ -627,7 +637,7 @@ return gvar; } -int smallGvarToC9x(int gvar) +int smallGvarExport(int gvar) { if (gvar > 110) { gvar = gvar - 128 - 10000; @@ -754,7 +764,7 @@ { if (curve.value != 0) { _curve_type = (unsigned int)curve.type; - _curve_value = smallGvarToEEPROM(curve.value); + _curve_value = smallGvarImport(curve.value); } else { _curve_type = 0; @@ -765,7 +775,7 @@ virtual void afterImport() { curve.type = (CurveReference::CurveRefType)_curve_type; - curve.value = smallGvarToC9x(_curve_value); + curve.value = smallGvarExport(_curve_value); qCDebug(eepromImport) << QString("imported CurveReference(%1)").arg(curve.toString()); } @@ -996,7 +1006,7 @@ else internalField.Append(new ZCharField<6>(this, mix.name)); } - else if (IS_TARANIS(board) && version >= 217) { + else if (IS_TARANIS(board) && version == 217) { internalField.Append(new UnsignedField<8>(this, _destCh)); internalField.Append(new UnsignedField<9>(this, mix.flightModes)); internalField.Append(new UnsignedField<2>(this, (unsigned int &)mix.mltpx)); @@ -1013,7 +1023,7 @@ internalField.Append(new UnsignedField<8>(this, mix.speedDown)); internalField.Append(new ZCharField<8>(this, mix.name)); } - else if (IS_ARM(board) && version >= 217) { + else if (IS_ARM(board) && version == 217) { internalField.Append(new UnsignedField<5>(this, _destCh)); internalField.Append(new UnsignedField<3>(this, mix.mixWarn)); internalField.Append(new UnsignedField<9>(this, mix.flightModes)); @@ -1172,7 +1182,7 @@ } else if (mix.curve.type == CurveReference::CURVE_REF_DIFF) { _curveMode = 0; - _curveParam = smallGvarToEEPROM(mix.curve.value); + _curveParam = smallGvarImport(mix.curve.value); } } else { @@ -1209,7 +1219,7 @@ mix.destCh = _destCh + 1; if (!IS_ARM(board) || (!IS_STM32(board) && version < 218) || version < 216) { if (!_curveMode) - mix.curve = CurveReference(CurveReference::CURVE_REF_DIFF, smallGvarToC9x(_curveParam)); + mix.curve = CurveReference(CurveReference::CURVE_REF_DIFF, smallGvarExport(_curveParam)); else if (_curveParam > 6) mix.curve = CurveReference(CurveReference::CURVE_REF_CUSTOM, _curveParam-6); else if (_curveParam < 0) @@ -1369,13 +1379,13 @@ virtual void beforeExport() { - _weight = smallGvarToEEPROM(expo.weight); + _weight = smallGvarImport(expo.weight); - if (IS_HORUS_OR_TARANIS(board) && version >= 216) { - _offset = smallGvarToEEPROM(expo.offset); + if ((IS_HORUS_OR_TARANIS(board) && version >= 216) || (IS_ARM(board) && version >= 218)) { + _offset = smallGvarImport(expo.offset); } - if (!IS_TARANIS(board) || version < 216) { + if (!IS_ARM(board) || (!IS_TARANIS(board) && version < 218) || version < 216) { if (expo.curve.type==CurveReference::CURVE_REF_FUNC && expo.curve.value) { _curveMode = true; _curveParam = expo.curve.value; @@ -1386,33 +1396,26 @@ } else { _curveMode = false; - _curveParam = smallGvarToEEPROM(expo.curve.value); + _curveParam = smallGvarImport(expo.curve.value); } } } virtual void afterImport() { - if (IS_STM32(board)) { - if (version < 216) { - if (expo.mode) { - expo.srcRaw = RawSource(SOURCE_TYPE_STICK, expo.chn); - } - } - } - else if (expo.mode) { + if ((IS_STM32(board) && version < 216 )|| (!IS_STM32(board) && expo.mode)) { expo.srcRaw = RawSource(SOURCE_TYPE_STICK, expo.chn); } - expo.weight = smallGvarToC9x(_weight); + expo.weight = smallGvarExport(_weight); - if (IS_STM32(board) && version >= 216) { - expo.offset = smallGvarToC9x(_offset); + if ((IS_STM32(board) && version >= 216) || (IS_ARM(board) && version >= 218)) { + expo.offset = smallGvarExport(_offset); } - if (!IS_ARM(board) || (!IS_STM32(board) && version < 218) || version < 216) { + if (!IS_ARM(board) || (!IS_TARANIS(board) && version < 218) || version < 216) { if (!_curveMode) - expo.curve = CurveReference(CurveReference::CURVE_REF_EXPO, smallGvarToC9x(_curveParam)); + expo.curve = CurveReference(CurveReference::CURVE_REF_EXPO, smallGvarExport(_curveParam)); else if (_curveParam > 6) expo.curve = CurveReference(CurveReference::CURVE_REF_CUSTOM, _curveParam-6); else @@ -2580,13 +2583,13 @@ bars.Append(new SourceField<16>(this, screen.body.bars[i].source, board, version, variant)); else bars.Append(new SourceField<8>(this, screen.body.bars[i].source, board, version, variant)); - bars.Append(new UnsignedField<16>(this, screen.body.bars[i].barMin)); - bars.Append(new UnsignedField<16>(this, screen.body.bars[i].barMax)); + bars.Append(new SignedField<16>(this, screen.body.bars[i].barMin)); + bars.Append(new SignedField<16>(this, screen.body.bars[i].barMax)); } else { bars.Append(new TelemetrySourceField<8>(this, screen.body.bars[i].source, board, version)); - bars.Append(new UnsignedField<8>(this, screen.body.bars[i].barMin)); - bars.Append(new UnsignedField<8>(this, screen.body.bars[i].barMax)); + bars.Append(new UnsignedField<8>(this, (unsigned &)screen.body.bars[i].barMin)); + bars.Append(new UnsignedField<8>(this, (unsigned &)screen.body.bars[i].barMax)); } } @@ -2777,7 +2780,7 @@ class FrskyField: public StructField { public: - FrskyField(DataField * parent, FrSkyData & frsky, Board::Type board, unsigned int version, unsigned int variant): + FrskyField(DataField * parent, FrSkyData & frsky, RSSIAlarmData & rssiAlarms, Board::Type board, unsigned int version, unsigned int variant): StructField(parent, "FrSky"), telemetryVarioSourceConversionTable(board, version), screenTypesConversionTable(board, version), @@ -2849,10 +2852,12 @@ Append(new SignedField<8>(this, frsky.varioCenterMin)); Append(new SignedField<8>(this, frsky.varioMin)); Append(new SignedField<8>(this, frsky.varioMax)); - for (int i=0; i<2; i++) { - Append(new ConversionField< UnsignedField<2> >(this, frsky.rssiAlarms[i].level, &rssiConversionTable[i], "RSSI")); - Append(new ConversionField< SignedField<6> >(this, frsky.rssiAlarms[i].value, -45+i*3)); - } + Append(new BoolField<1>(this, rssiAlarms.disabled)); + Append(new SpareBitsField<1>(this)); + Append(new ConversionField >(this, rssiAlarms.warning, -45)); + Append(new SpareBitsField<2>(this)); + Append(new ConversionField >(this, rssiAlarms.critical, -42)); + if (version == 216) { Append(new BoolField<1>(this, frsky.mAhPersistent)); Append(new UnsignedField<15>(this, frsky.storedMah)); @@ -2881,8 +2886,8 @@ Append(new SignedField<4>(this, frsky.varioMin, "Vario Min")); Append(new SignedField<4>(this, frsky.varioMax)); for (int i=0; i<2; i++) { - Append(new ConversionField< UnsignedField<2> >(this, frsky.rssiAlarms[i].level, &rssiConversionTable[i], "RSSI level")); - Append(new ConversionField< SignedField<6> >(this, frsky.rssiAlarms[i].value, -45+i*3, 0, 0, 100, "RSSI value")); + Append(new ConversionField< UnsignedField<2> >(this, rssiAlarms.level[i], &rssiConversionTable[i], "RSSI level")); + Append(new ConversionField< SignedField<6> >(this, i ==0 ? rssiAlarms.warning : rssiAlarms.critical, -45+i*3, 0, 0, 100, "RSSI value")); } for (int i=0; i<2; i++) { Append(new FrskyScreenField(this, frsky.screens[i], board, version, variant)); @@ -3221,18 +3226,19 @@ if (board != BOARD_STOCK && (board != BOARD_M128 || version < 215)) { for (int i=0; i= 218) { - internalField.Append(new ZCharField<3>(this, modelData.gvars_names[i], "GVar name")); - internalField.Append(new SpareBitsField<12>(this)); // TODO min - internalField.Append(new SpareBitsField<12>(this)); // TODO max - internalField.Append(new BoolField<1>(this, modelData.gvars_popups[i])); - internalField.Append(new SpareBitsField<1>(this)); - internalField.Append(new SpareBitsField<2>(this)); + internalField.Append(new ZCharField<3>(this, modelData.gvarData[i].name, "GVar name")); + internalField.Append(new UnsignedField<12>(this, (unsigned &)modelData.gvarData[i].min)); + internalField.Append(new UnsignedField<12>(this, (unsigned &)modelData.gvarData[i].max)); + internalField.Append(new BoolField<1>(this, modelData.gvarData[i].popup)); + internalField.Append(new UnsignedField<1>(this, modelData.gvarData[i].prec)); + internalField.Append(new UnsignedField<2>(this, modelData.gvarData[i].unit)); internalField.Append(new SpareBitsField<4>(this)); } else { - internalField.Append(new ZCharField<6>(this, modelData.gvars_names[i], "GVar name")); + internalField.Append(new ZCharField<3>(this, modelData.gvarData[i].name, "GVar name")); + internalField.Append(new SpareBitsField<3*8>(this)); if (version >= 216) { - internalField.Append(new BoolField<1>(this, modelData.gvars_popups[i])); + internalField.Append(new BoolField<1>(this, modelData.gvarData[i].popup)); internalField.Append(new SpareBitsField<7>(this)); } } @@ -3246,7 +3252,7 @@ } if ((board != BOARD_STOCK && (board != BOARD_M128 || version < 215)) || (variant & FRSKY_VARIANT)) { - internalField.Append(new FrskyField(this, modelData.frsky, board, version, variant)); + internalField.Append(new FrskyField(this, modelData.frsky, modelData.rssiAlarms, board, version, variant)); } else if ((board == BOARD_STOCK || board == BOARD_M128) && (variant & MAVLINK_VARIANT)) { internalField.Append(new MavlinkField(this, modelData.mavlink, board, version)); @@ -3423,8 +3429,18 @@ // qDebug() << QString("before export model") << modelData.name; for (int module=0; module<3; module++) { - if (modelData.moduleData[module].protocol >= PULSES_PXX_XJT_X16 && modelData.moduleData[module].protocol <= PULSES_PXX_XJT_LR12) { - subprotocols[module] = modelData.moduleData[module].protocol - PULSES_PXX_XJT_X16; + if ((modelData.moduleData[module].protocol >= PULSES_PXX_XJT_X16 && modelData.moduleData[module].protocol <= PULSES_PXX_XJT_LR12) || + modelData.moduleData[module].protocol == PULSES_PXX_R9M) { + if (! (modelData.moduleData[module].protocol == PULSES_PXX_R9M)) { + subprotocols[module] = modelData.moduleData[module].protocol - PULSES_PXX_XJT_X16; + } + int pxxByte = (modelData.moduleData[module].pxx.power & 0x03) + | modelData.moduleData[module].pxx.receiver_telem_off << 4 + | modelData.moduleData[module].pxx.receiver_channel_9_16 << 5; + modelData.moduleData[module].ppm.delay = 300 + 50 * pxxByte; + modelData.moduleData[module].ppm.pulsePol = modelData.moduleData[module].pxx.external_antenna; + modelData.moduleData[module].ppm.outputType = modelData.moduleData[module].pxx.sport_out; + } else if (modelData.moduleData[module].protocol >= PULSES_LP45 && modelData.moduleData[module].protocol <= PULSES_DSMX) { subprotocols[module] = modelData.moduleData[module].protocol - PULSES_LP45; @@ -3499,6 +3515,17 @@ modelData.moduleData[module].multi.lowPowerMode = modelData.moduleData[module].ppm.outputType; modelData.moduleData[module].multi.autoBindMode = modelData.moduleData[module].ppm.pulsePol; } + + if ((modelData.moduleData[module].protocol >= PULSES_PXX_XJT_X16 && modelData.moduleData[module].protocol <= PULSES_PXX_XJT_LR12) || + modelData.moduleData[module].protocol == PULSES_PXX_R9M) { + // Do the same for pxx + unsigned int pxxByte = (unsigned int)((modelData.moduleData[module].ppm.delay - 300) / 50); + modelData.moduleData[module].pxx.power = pxxByte & 0x03; + modelData.moduleData[module].pxx.receiver_telem_off = static_cast(pxxByte & (1 << 4)); + modelData.moduleData[module].pxx.receiver_channel_9_16 = static_cast(pxxByte & (1 << 5)); + modelData.moduleData[module].pxx.sport_out = modelData.moduleData[module].ppm.outputType; + modelData.moduleData[module].pxx.external_antenna = modelData.moduleData[module].ppm.pulsePol; + } } if (IS_TARANIS(board) && version < 217 && modelData.moduleData[1].protocol != PULSES_OFF) { @@ -3656,22 +3683,25 @@ internalField.Append(new UnsignedField<8>(this, generalData.backlightBright)); if (version < 218) internalField.Append(new SignedField<8>(this, generalData.txCurrentCalibration)); if (version >= 213) { - if (version < 218) internalField.Append(new SignedField<8>(this, generalData.temperatureWarn)); // TODO + if (version < 218) internalField.Append(new SignedField<8>(this, generalData.temperatureWarn)); if (version < 218) internalField.Append(new UnsignedField<8>(this, generalData.mAhWarn)); if (version < 218) internalField.Append(new UnsignedField<16>(this, generalData.mAhUsed)); internalField.Append(new UnsignedField<32>(this, generalData.globalTimer)); - if (version < 218) internalField.Append(new SignedField<8>(this, generalData.temperatureCalib)); // TODO - internalField.Append(new UnsignedField<8>(this, generalData.btBaudrate)); // TODO - if (version < 218) internalField.Append(new BoolField<8>(this, generalData.optrexDisplay)); //TODO - if (version < 218) internalField.Append(new UnsignedField<8>(this, generalData.sticksGain)); // TODO + if (version < 218) internalField.Append(new SignedField<8>(this, generalData.temperatureCalib)); + internalField.Append(new UnsignedField<4>(this, generalData.bluetoothBaudrate)); + internalField.Append(new UnsignedField<4>(this, generalData.bluetoothMode)); + if (version < 218) internalField.Append(new BoolField<8>(this, generalData.optrexDisplay)); + if (version < 218) internalField.Append(new UnsignedField<8>(this, generalData.sticksGain)); } if (version >= 214) { - if (version < 218) internalField.Append(new UnsignedField<8>(this, generalData.rotarySteps)); // TODO + if (version < 218) internalField.Append(new UnsignedField<8>(this, generalData.rotarySteps)); internalField.Append(new UnsignedField<8>(this, generalData.countryCode)); internalField.Append(new UnsignedField<1>(this, generalData.imperial)); if (version >= 218) { internalField.Append(new BoolField<1>(this, generalData.jitterFilter)); - internalField.Append(new SpareBitsField<6>(this)); + internalField.Append(new BoolField<1>(this, generalData.disableRssiPoweroffAlarm)); + internalField.Append(new UnsignedField<2>(this, generalData.usbMode)); + internalField.Append(new SpareBitsField<3>(this)); } else { internalField.Append(new SpareBitsField<7>(this)); @@ -3741,6 +3771,16 @@ internalField.Append(new UnsignedField<8>(this, generalData.backlightColor)); } } + else if (IS_SKY9X(board) && version >= 218) { + internalField.Append(new SignedField<8>(this, generalData.txCurrentCalibration)); + internalField.Append(new SignedField<8>(this, generalData.temperatureWarn)); + internalField.Append(new UnsignedField<8>(this, generalData.mAhWarn)); + internalField.Append(new UnsignedField<16>(this, generalData.mAhUsed)); + internalField.Append(new SignedField<8>(this, generalData.temperatureCalib)); + internalField.Append(new BoolField<8>(this, generalData.optrexDisplay)); + internalField.Append(new UnsignedField<8>(this, generalData.sticksGain)); + internalField.Append(new UnsignedField<8>(this, generalData.rotarySteps)); + } if (IS_TARANIS_X9E(board)) internalField.Append(new SpareBitsField<64>(this)); // switchUnlockStates @@ -3790,7 +3830,7 @@ } if (IS_HORUS(board)) { - internalField.Append(new BoolField<1>(this, generalData.bluetoothEnable)); + internalField.Append(new SpareBitsField<1>(this)); internalField.Append(new UnsignedField<7>(this, generalData.backlightOffBright)); internalField.Append(new ZCharField<10>(this, generalData.bluetoothName, "Bluetooth name")); } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/firmwares/opentx/opentxeeprom.h opentx-companion22-2.2.1~ppa01~xenial/companion/src/firmwares/opentx/opentxeeprom.h --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/firmwares/opentx/opentxeeprom.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/firmwares/opentx/opentxeeprom.h 2017-10-31 16:16:43.000000000 +0000 @@ -98,13 +98,11 @@ addConversion(PULSES_DSM2, val++); addConversion(PULSES_DSMX, val++); } - if (IS_HORUS_OR_TARANIS(board)) { + if (IS_ARM(board)) { addConversion(PULSES_CROSSFIRE, val++); addConversion(PULSES_MULTIMODULE, val++); - } - else if (IS_ARM(board)) { - val++; - addConversion(PULSES_MULTIMODULE, val++); + addConversion(PULSES_PXX_R9M, val++); + addConversion(PULSES_SBUS, val++); } } }; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/firmwares/opentx/opentxinterface.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/firmwares/opentx/opentxinterface.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/firmwares/opentx/opentxinterface.cpp 2017-04-29 16:57:04.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/firmwares/opentx/opentxinterface.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -30,8 +30,11 @@ using namespace Board; -#define OPENTX_FIRMWARE_DOWNLOADS "http://downloads-22.open-tx.org/firmware" -#define OPENTX_NIGHT_FIRMWARE_DOWNLOADS "http://downloads-22.open-tx.org/nightly/firmware" +const char * const OPENTX_FIRMWARE_DOWNLOAD_URL[] = { + "https://downloads.open-tx.org/2.2/release/firmware", + "https://downloads.open-tx.org/2.2/rc/firmware", + "https://downloads.open-tx.org/2.2/nightlies/firmware" +}; #define FILE_TYP_GENERAL 1 #define FILE_TYP_MODEL 2 @@ -107,7 +110,7 @@ return checkVariant(settings.version, settings.variant); } else { - std::cout << " error when loading general settings"; + qWarning() << " error when loading general settings"; return false; } } @@ -180,7 +183,9 @@ unsigned long OpenTxEepromInterface::load(RadioData &radioData, const uint8_t * eeprom, int size) { - std::cout << "trying " << getName() << " import..."; + QDebug dbg = qDebug(); + dbg.setAutoInsertSpaces(false); + dbg << "trying " << getName() << " import..."; std::bitset errors; @@ -193,7 +198,7 @@ } } if (notnull) { - std::cout << " wrong size (" << size << ")\n"; + dbg << " wrong size (" << size << ")"; errors.set(WRONG_SIZE); return errors.to_ulong(); } @@ -204,14 +209,14 @@ } } else { - std::cout << " wrong size (" << size << "/" << Boards::getEEpromSize(board) << ")\n"; + dbg << " wrong size (" << size << "/" << Boards::getEEpromSize(board) << ")"; errors.set(WRONG_SIZE); return errors.to_ulong(); } } if (!efile->EeFsOpen((uint8_t *) eeprom, size, board)) { - std::cout << " wrong file system\n"; + dbg << " wrong file system"; errors.set(WRONG_FILE_SYSTEM); return errors.to_ulong(); } @@ -220,12 +225,12 @@ uint8_t version; if (efile->readRlc2(&version, 1) != 1) { - std::cout << " no\n"; + dbg << " no"; errors.set(UNKNOWN_ERROR); return errors.to_ulong(); } - std::cout << " version " << (unsigned int) version; + dbg << " version " << (unsigned int) version; EepromLoadErrors version_error = checkVersion(version); if (version_error == OLD_VERSION) { @@ -234,24 +239,24 @@ ShowEepromWarnings(NULL, QObject::tr("Warning"), errors.to_ulong()); } else if (version_error == NOT_OPENTX) { - std::cout << " not open9x\n"; + dbg << " not open9x"; errors.set(version_error); return errors.to_ulong(); } if (!loadRadioSettingsFromRLE(radioData.generalSettings, efile, version)) { - std::cout << " ko\n"; + dbg << " ko"; errors.set(UNKNOWN_ERROR); return errors.to_ulong(); } - std::cout << " variant " << radioData.generalSettings.variant; + dbg << " variant " << radioData.generalSettings.variant; if (getCurrentFirmware()->getCapability(Models) == 0) { radioData.models.resize(firmware->getCapability(Models)); } for (int i = 0; i < firmware->getCapability(Models); i++) { if (i < (int)radioData.models.size() && !loadModelFromRLE(radioData.models[i], efile, i, version, radioData.generalSettings.variant)) { - std::cout << " ko\n"; + dbg << " ko"; errors.set(UNKNOWN_ERROR); if (getCurrentFirmware()->getCapability(Models) == 0) { radioData.models.resize(i); @@ -259,7 +264,7 @@ return errors.to_ulong(); } } - std::cout << " ok\n"; + dbg << " ok"; errors.set(ALL_OK); return errors.to_ulong(); } @@ -332,7 +337,7 @@ } for (int i = 0; i < getCurrentFirmware()->getCapability(Models); i++) { - if (!radioData.models[i].isEmpty()) { + if (i < (int)radioData.models.size() && !radioData.models[i].isEmpty()) { OpenTxModelData generator((ModelData &)radioData.models[i], board, version, variant); // generator.Dump(); QByteArray data; @@ -538,6 +543,16 @@ return 0; case MaxVolume: return (IS_ARM(board) ? 23 : 7); + case MaxContrast: + if (IS_TARANIS_X7(board)) + return 30; + else + return 45; + case MinContrast: + if (IS_TARANIS_X9(board)) + return 0; + else + return 10; case HasSoundMixer: return (IS_ARM(board) ? 1 : 0); case ExtraInputs: @@ -559,7 +574,7 @@ case ChannelsName: return (IS_ARM(board) ? (HAS_LARGE_LCD(board) ? 6 : 4) : 0); case HasCvNames: - return (IS_HORUS_OR_TARANIS(board) ? 1 : 0); + return (IS_ARM(board) ? 1 : 0); case Telemetry: if (IS_2560(board) || IS_ARM(board) || id.contains("frsky") || id.contains("telemetrez")) return TM_HASTELEMETRY | TM_HASOFFSET | TM_HASWSHH; @@ -744,7 +759,7 @@ }; return CHECK_IN_ARRAY(pots, index); } - else if (IS_HORUS(board)) { + else if (IS_HORUS_X12S(board)) { const QString pots[] = { QObject::tr("S1"), QObject::tr("6P"), @@ -758,6 +773,16 @@ }; return CHECK_IN_ARRAY(pots, index); } + else if (IS_HORUS_X10(board)) { + const QString pots[] = { + QObject::tr("S1"), + QObject::tr("6P"), + QObject::tr("S2"), + QObject::tr("LS"), + QObject::tr("RS") + }; + return CHECK_IN_ARRAY(pots, index); + } else { return "???"; } @@ -798,11 +823,13 @@ case PULSES_PXX_XJT_X16: case PULSES_PXX_XJT_D8: case PULSES_PXX_XJT_LR12: + case PULSES_PXX_R9M: //case PULSES_PXX_DJT: // Unavailable for now case PULSES_LP45: case PULSES_DSM2: case PULSES_DSMX: case PULSES_CROSSFIRE: + case PULSES_SBUS: return 1; case PULSES_MULTIMODULE: return id.contains("multimodule") ? 1 : 0; @@ -830,9 +857,11 @@ case PULSES_PXX_XJT_X16: case PULSES_PXX_XJT_D8: case PULSES_PXX_XJT_LR12: + case PULSES_PXX_R9M: case PULSES_LP45: case PULSES_DSM2: case PULSES_DSMX: + case PULSES_SBUS: return 1; case PULSES_MULTIMODULE: return id.contains("multimodule") ? 1 : 0; @@ -939,29 +968,29 @@ efile->openRd(i); int sz = efile->readRlc2(tmp, sizeof(tmp)); if (sz == 849) { - std::cout << " warning: M128 variant not set (but model size seems ok)"; + qWarning() << " warning: M128 variant not set (but model size seems ok)"; return true; } } } - std::cout << " wrong variant (" << variant << ")"; + qWarning() << " wrong variant (" << variant << ")"; return false; } else if (IS_TARANIS_X9E(board)) { if (variant != TARANIS_X9E_VARIANT) { - std::cout << " wrong variant (" << variant << ")"; + qWarning() << " wrong variant (" << variant << ")"; return false; } } else if (IS_TARANIS_X7(board)) { if (variant != TARANIS_X7_VARIANT) { - std::cout << " wrong variant (" << variant << ")"; + qWarning() << " wrong variant (" << variant << ")"; return false; } } else if (IS_TARANIS(board)) { if (variant != 0) { - std::cout << " wrong variant (" << variant << ")"; + qWarning() << " wrong variant (" << variant << ")"; return false; } } @@ -994,10 +1023,12 @@ { std::bitset errors; - std::cout << "trying " << getName() << " backup import..."; + QDebug dbg = qDebug(); + dbg.setAutoInsertSpaces(false); + dbg << "trying " << getName() << " backup import..."; if (esize < 8 || memcmp(eeprom, "o9x", 3) != 0) { - std::cout << " no\n"; + dbg << " no\n"; errors.set(WRONG_SIZE); return errors.to_ulong(); } @@ -1014,13 +1045,13 @@ backupBoard = BOARD_GRUVIN9X; break; default: - std::cout << " unknown board\n"; + dbg << " unknown board"; errors.set(UNKNOWN_BOARD); return errors.to_ulong(); } if (backupBoard != board) { - std::cout << " not right board\n"; + dbg << " not right board"; errors.set(WRONG_BOARD); return errors.to_ulong(); } @@ -1030,7 +1061,7 @@ uint16_t size = ((uint16_t) eeprom[7] << 8) + eeprom[6]; uint16_t variant = ((uint16_t) eeprom[9] << 8) + eeprom[8]; - std::cout << " version " << (unsigned int) version << " "; + dbg << " version " << (unsigned int) version << " "; EepromLoadErrors version_error = checkVersion(version); if (version_error == OLD_VERSION) { @@ -1038,42 +1069,38 @@ errors.set(HAS_WARNINGS); } else if (version_error == NOT_OPENTX) { - std::cout << " not open9x\n"; + dbg << " not open9x"; errors.set(version_error); return errors.to_ulong(); } if (size > esize - 8) { - std::cout << " wrong size\n"; + dbg << " wrong size"; errors.set(WRONG_SIZE); return errors.to_ulong(); } if (bcktype == 'M') { if (!loadModelFromBackup(radioData.models[index], &eeprom[8], size, version, variant)) { - std::cout << " ko\n"; + dbg << " ko"; errors.set(UNKNOWN_ERROR); return errors.to_ulong(); } } else { - std::cout << " backup type not supported\n"; + dbg << " backup type not supported"; errors.set(BACKUP_NOT_SUPPORTED); return errors.to_ulong(); } - std::cout << " ok\n"; + dbg << " ok"; errors.set(ALL_OK); return errors.to_ulong(); } QString OpenTxFirmware::getFirmwareBaseUrl() { -#if defined(ALLOW_NIGHTLY_BUILDS) - return (g.useFirmwareNightlyBuilds() ? OPENTX_NIGHT_FIRMWARE_DOWNLOADS : OPENTX_FIRMWARE_DOWNLOADS); -#else - return OPENTX_FIRMWARE_DOWNLOADS; -#endif + return OPENTX_FIRMWARE_DOWNLOAD_URL[g.boundedOpenTxBranch()]; } QString OpenTxFirmware::getFirmwareUrl() @@ -1124,13 +1151,8 @@ addOpenTxArmOptions(firmware); firmware->addOption("noheli", QObject::tr("Disable HELI menu and cyclic mix support")); firmware->addOption("nogvars", QObject::tr("Disable Global variables")); - firmware->addOption("lua", QObject::tr("Support for Lua model scripts")); + firmware->addOption("lua", QObject::tr("Enable Lua custom scripts screen")); firmware->addOption("luac", QObject::tr("Enable Lua compiler")); - firmware->addOption("bindopt", QObject::tr("Enable bindings options")); - Option usb_options[] = {{"massstorage", QObject::tr("Instead of Joystick emulation, USB connection is Mass Storage (as in the Bootloader)")}, - {"cli", QObject::tr("Instead of Joystick emulation, USB connection is Command Line Interface")}, - {NULL}}; - firmware->addOptions(usb_options); } void addOpenTxTaranisOptions(OpenTxFirmware * firmware) @@ -1217,26 +1239,24 @@ registerOpenTxFirmware(firmware); /* FrSky X7 board */ - firmware = new OpenTxFirmware("opentx-x7", QObject::tr("FrSky Taranis X7"), BOARD_TARANIS_X7); + firmware = new OpenTxFirmware("opentx-x7", QObject::tr("FrSky Taranis X7 / X7S"), BOARD_TARANIS_X7); // No mixersmon for now addOpenTxFrskyOptions(firmware); firmware->addOption("internalppm", QObject::tr("Support for PPM internal module hack")); firmware->addOption("sqt5font", QObject::tr("Use alternative SQT5 font")); registerOpenTxFirmware(firmware); - /* FrSky Horus board */ - firmware = new OpenTxFirmware("opentx-x12s", QObject::tr("FrSky Horus"), BOARD_X12S); + /* FrSky X10 board */ + firmware = new OpenTxFirmware("opentx-x10", QObject::tr("FrSky Horus X10 / X10S"), BOARD_X10); addOpenTxFrskyOptions(firmware); - firmware->addOption("pcbdev", QObject::tr("Use ONLY with first DEV pcb version")); registerOpenTxFirmware(firmware); - - /* FrSky X10 board */ -/* Disabled for now - firmware = new OpenTxFirmware("opentx-x10", QObject::tr("FrSky X10"), BOARD_X10); + /* FrSky Horus board */ + firmware = new OpenTxFirmware("opentx-x12s", QObject::tr("FrSky Horus X12S"), BOARD_X12S); addOpenTxFrskyOptions(firmware); + firmware->addOption("pcbdev", QObject::tr("Use ONLY with first DEV pcb version")); registerOpenTxFirmware(firmware); -*/ + /* 9XR-Pro */ firmware = new OpenTxFirmware("opentx-9xrpro", QObject::tr("Turnigy 9XR-PRO"), BOARD_9XRPRO); firmware->addOption("heli", QObject::tr("Enable HELI menu and cyclic mix support")); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/fwpreferencesdialog.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/fwpreferencesdialog.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/fwpreferencesdialog.cpp 2017-05-14 17:18:57.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/fwpreferencesdialog.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -21,13 +21,16 @@ #include "fwpreferencesdialog.h" #include "ui_fwpreferencesdialog.h" #include "mainwindow.h" -#include "eeprominterface.h" #include "helpers.h" #include "appdata.h" -#include -#include -FirmwarePreferencesDialog::FirmwarePreferencesDialog(QWidget *parent) : +const char * const OPENTX_SDCARD_DOWNLOAD_URL[] = { + "https://downloads.open-tx.org/2.2/release/sdcard/", + "https://downloads.open-tx.org/2.2/rc/sdcard/", + "https://downloads.open-tx.org/2.2/nightlies/sdcard/" +}; + +FirmwarePreferencesDialog::FirmwarePreferencesDialog(QWidget * parent) : QDialog(parent), ui(new Ui::FirmwarePreferencesDialog) { @@ -52,26 +55,26 @@ void FirmwarePreferencesDialog::on_checkFWUpdates_clicked() { - MainWindow * mw = (MainWindow *)this->parent(); + MainWindow * mw = qobject_cast(this->parent()); mw->checkForFirmwareUpdate(); initSettings(); } void FirmwarePreferencesDialog::on_fw_dnld_clicked() { - MainWindow * mw = (MainWindow *)this->parent(); + MainWindow * mw = qobject_cast(this->parent()); mw->dowloadLastFirmwareUpdate(); initSettings(); } void FirmwarePreferencesDialog::on_sd_dnld_clicked() { - QString url = "http://downloads.open-tx.org/2.2/sdcard/"; + QString url = OPENTX_SDCARD_DOWNLOAD_URL[g.boundedOpenTxBranch()]; QString fwType = g.profile[g.id()].fwType(); QStringList list = fwType.split("-"); QString firmware = QString("%1-%2").arg(list[0]).arg(list[1]); - url.append(QString("%1/").arg(firmware)); + if (g.boundedOpenTxBranch() != BRANCH_NIGHTLY_UNSTABLE) { + url.append(QString("%1/").arg(firmware)); + } QDesktopServices::openUrl(url); } - - diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/generaledit/generalsetup.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/generaledit/generalsetup.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/generaledit/generalsetup.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/generaledit/generalsetup.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -27,11 +27,10 @@ { ui->setupUi(this); - QLabel * pmsl[] = {ui->ro_label,ui->ro1_label,ui->ro2_label,ui->ro3_label,ui->ro4_label,ui->ro5_label,ui->ro6_label,ui->ro7_label,ui->ro8_label, NULL}; - QSlider * tpmsld[] = {ui->chkSA, ui->chkSB, ui->chkSC, ui->chkSD, ui->chkSE, ui->chkSF, ui->chkSG, ui->chkSH, NULL}; + QLabel *pmsl[] = {ui->ro_label, ui->ro1_label, ui->ro2_label, ui->ro3_label, ui->ro4_label, ui->ro5_label, ui->ro6_label, ui->ro7_label, ui->ro8_label, NULL}; + QSlider *tpmsld[] = {ui->chkSA, ui->chkSB, ui->chkSC, ui->chkSD, ui->chkSE, ui->chkSF, ui->chkSG, ui->chkSH, NULL}; if (IS_TARANIS(firmware->getBoard())) { - ui->contrastSB->setMinimum(0); if (firmware->getId().contains("readonly")) { uint16_t switchstate = generalSettings.switchUnlockStates; ui->chkSA->setValue(switchstate & 0x3); @@ -44,27 +43,27 @@ switchstate >>= 2; ui->chkSE->setValue(switchstate & 0x3); switchstate >>= 2; - ui->chkSF->setValue((switchstate & 0x3)/2); + ui->chkSF->setValue((switchstate & 0x3) / 2); switchstate >>= 2; ui->chkSG->setValue(switchstate & 0x3); switchstate >>= 2; ui->chkSH->setValue(switchstate & 0x3); } else { - for (int i=0; pmsl[i]; i++) { + for (int i = 0; pmsl[i]; i++) { pmsl[i]->hide(); } - for (int i=0; tpmsld[i]; i++) { + for (int i = 0; tpmsld[i]; i++) { tpmsld[i]->hide(); } this->layout()->removeItem(ui->TaranisReadOnlyUnlock); } } else { - for (int i=0; pmsl[i]; i++) { + for (int i = 0; pmsl[i]; i++) { pmsl[i]->hide(); } - for (int i=0; tpmsld[i]; i++) { + for (int i = 0; tpmsld[i]; i++) { tpmsld[i]->hide(); } this->layout()->removeItem(ui->TaranisReadOnlyUnlock); @@ -112,10 +111,10 @@ ui->varioVolume_SL->setValue(generalSettings.varioVolume); ui->bgVolume_SL->setValue(generalSettings.backgroundVolume); ui->wavVolume_SL->setValue(generalSettings.wavVolume); - ui->varioP0_SB->setValue(700+(generalSettings.varioPitch*10)); + ui->varioP0_SB->setValue(700 + (generalSettings.varioPitch * 10)); updateVarioPitchRange(); - ui->varioPMax_SB->setValue(700+(generalSettings.varioPitch*10)+1000+(generalSettings.varioRange*10)); - ui->varioR0_SB->setValue(500+(generalSettings.varioRepeat*10)); + ui->varioPMax_SB->setValue(700 + (generalSettings.varioPitch * 10) + 1000 + (generalSettings.varioRange * 10)); + ui->varioR0_SB->setValue(500 + (generalSettings.varioRepeat * 10)); } if (!firmware->getCapability(HasFAIMode)) { @@ -152,11 +151,22 @@ ui->adjustRTC->hide(); } + if (IS_STM32(firmware->getBoard())){ + ui->usbModeCB->setCurrentIndex(generalSettings.usbMode); + } + else { + ui->usbModeLabel->hide(); + ui->usbModeCB->hide(); + } + if (!firmware->getCapability(OptrexDisplay)) { ui->label_displayType->hide(); ui->displayTypeCB->setDisabled(true); ui->displayTypeCB->hide(); } + else { + ui->displayTypeCB->setCurrentIndex(generalSettings.optrexDisplay); + } if (!firmware->getCapability(HasVolume)) { ui->volume_SB->hide(); @@ -197,7 +207,7 @@ } int reCount = firmware->getCapability(RotaryEncoders); - if (reCount==0) { + if (reCount == 0) { ui->re_label->hide(); ui->re_CB->hide(); } @@ -205,13 +215,23 @@ populateRotEncCB(reCount); } + ui->contrastSB->setMinimum(firmware->getCapability(MinContrast)); + ui->contrastSB->setMaximum(firmware->getCapability(MaxContrast)); ui->contrastSB->setValue(generalSettings.contrast); + ui->battwarningDSB->setValue((double)generalSettings.vBatWarn/10); ui->backlightautoSB->setValue(generalSettings.backlightDelay*5); ui->inactimerSB->setValue(generalSettings.inactivityTimer); - ui->memwarnChkB->setChecked(!generalSettings.disableMemoryWarning); //Default is zero=checked - ui->alarmwarnChkB->setChecked(!generalSettings.disableAlarmWarning);//Default is zero=checked + ui->memwarnChkB->setChecked(!generalSettings.disableMemoryWarning); // Default is zero=checked + ui->alarmwarnChkB->setChecked(!generalSettings.disableAlarmWarning); // Default is zero=checked + + if (IS_ARM(firmware->getBoard())) { + ui->rssiPowerOffWarnChkB->setChecked(!generalSettings.disableRssiPoweroffAlarm); // Default is zero=checked + } + else { + ui->rssiPowerOffWarnChkB->hide(); + } if (IS_HORUS(firmware->getBoard())) { ui->splashScreenChkB->hide(); @@ -325,6 +345,14 @@ } } +void GeneralSetupPanel::on_usbModeCB_currentIndexChanged(int index) +{ + if (!lock) { + generalSettings.usbMode = ui->usbModeCB->currentIndex(); + emit modified(); + } +} + void GeneralSetupPanel::on_backlightColor_SL_valueChanged() { if (!lock) { @@ -607,18 +635,24 @@ emit modified(); } -void GeneralSetupPanel::on_memwarnChkB_stateChanged(int ) +void GeneralSetupPanel::on_memwarnChkB_stateChanged(int) { generalSettings.disableMemoryWarning = ui->memwarnChkB->isChecked() ? 0 : 1; emit modified(); } -void GeneralSetupPanel::on_alarmwarnChkB_stateChanged(int ) +void GeneralSetupPanel::on_alarmwarnChkB_stateChanged(int) { generalSettings.disableAlarmWarning = ui->alarmwarnChkB->isChecked() ? 0 : 1; emit modified(); } +void GeneralSetupPanel::on_rssiPowerOffWarnChkB_stateChanged(int) +{ + generalSettings.disableRssiPoweroffAlarm = ui->rssiPowerOffWarnChkB->isChecked() ? 0 : 1; + emit modified(); +} + void GeneralSetupPanel::on_beeperCB_currentIndexChanged(int index) { generalSettings.beeperMode = (GeneralSettings::BeeperMode)(index-2); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/generaledit/generalsetup.h opentx-companion22-2.2.1~ppa01~xenial/companion/src/generaledit/generalsetup.h --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/generaledit/generalsetup.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/generaledit/generalsetup.h 2017-10-31 16:16:43.000000000 +0000 @@ -40,6 +40,7 @@ void on_splashScreenChkB_stateChanged(int); void on_splashScreenDuration_currentIndexChanged(int index); void on_alarmwarnChkB_stateChanged(int); + void on_rssiPowerOffWarnChkB_stateChanged(int); void on_gpsFormatCB_currentIndexChanged(int index); void on_displayTypeCB_currentIndexChanged(int index); void on_BLBright_SB_editingFinished(); @@ -58,6 +59,7 @@ void on_hapticmodeCB_currentIndexChanged(int index); void on_hapticLengthCB_currentIndexChanged(int index); void on_backlightswCB_currentIndexChanged(int index); + void on_usbModeCB_currentIndexChanged(int index); void on_backlightColor_SL_valueChanged(); void on_mavbaud_CB_currentIndexChanged(int index); void on_voiceLang_CB_currentIndexChanged(int index); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/generaledit/generalsetup.ui opentx-companion22-2.2.1~ppa01~xenial/companion/src/generaledit/generalsetup.ui --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/generaledit/generalsetup.ui 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/generaledit/generalsetup.ui 2017-10-31 16:16:43.000000000 +0000 @@ -6,8 +6,8 @@ 0 0 - 782 - 694 + 809 + 801 @@ -1121,8 +1121,74 @@ QLayout::SetDefaultConstraint - - + + + + + 0 + 0 + + + + + 16777215 + 16777215 + + + + <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0//EN" "http://www.w3.org/TR/REC-html40/strict.dtd"> +<html><head><meta name="qrichtext" content="1" /><style type="text/css"> +p, li { white-space: pre-wrap; } +</style></head><body style=" font-family:'MS Shell Dlg 2'; font-size:8.25pt; font-weight:400; font-style:normal;"> +<p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;"><span style=" text-decoration: underline;">Warnings</span></p> +<p style="-qt-paragraph-type:empty; margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;"></p> +<p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;">These will define startup warnings.</p> +<p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;">Throttle warning - will alert if the throttle is not at idle during startup</p> +<p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;">Switch warning - will alert if switches are not in their defaul position</p> +<p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;">Memory warning - will alert if there's not a lot of memory left</p> +<p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;">Silent mode warning - will alert you if the beeper is set to quiet (0)</p></body></html> + + + + + + true + + + + + + + + 0 + 0 + + + + + 0 + 0 + + + + RSSI Poweroff Warning + + + + + + + + 0 + 0 + + + + + 0 + 22 + + @@ -1130,230 +1196,435 @@ - Mode selection: - -Mode 1: - Left stick: Elevator, Rudder - Right stick: Throttle, Aileron - -Mode 2: - Left stick: Throttle, Rudder - Right stick: Elevator, Aileron - -Mode 3: - Left stick: Elevator, Aileron - Right stick: Throttle, Rudder - -Mode 4: - Left stick: Throttle, Aileron - Right stick: Elevator, Rudder + Beeper volume - - - - 1 +0 - Quiet. No beeps at all. +1 - No Keys. Normal beeps but menu keys do not beep. +2 - Normal. +3 - Loud. +4 - Extra loud. - Mode 1 (RUD ELE THR AIL) + Quiet - Mode 2 (RUD THR ELE AIL) + Alarms Only - Mode 3 (AIL ELE THR RUD) + No Keys - Mode 4 (AIL THR ELE RUD) + All - - - - + + + + + 0 + 0 + - - + + + 0 + 0 + - - <html><head/><body><p>Channel order</p><p><br/></p><p>Defines the order of the default mixes created on a new model.</p></body></html> + + Beeper Mode - - 0 + + + + + + + 0 + 0 + + + + + 0 + 22 + - R E T A - - - - - R E A T + X-Short - R T E A + Short - R T A E + Normal - R A E T + Long - R A T E + X-Long + + + + + + + 0 + 0 + + + + + 0 + 0 + + + + Beeper Length + + + + + + + + 0 + 0 + + + + + 0 + 0 + + + + Haptic Mode + + + + + + + Qt::Vertical + + + + 20 + 40 + + + + + + + + Measurement Units + + + + + + + + 0 + 0 + + + + Play Delay (switch mid position) + + + + + + + + 0 + 0 + + + + + 0 + 22 + + - E R T A + X-Short - E R A T + Short - E T R A + Normal - E T A R + Long - E A R T - - - - - E A T R - - - - - T R E A - - - - - T R A E + X-Long + + + + + + + 0 + 0 + + + + + 16777215 + 16777215 + + + + <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0//EN" "http://www.w3.org/TR/REC-html40/strict.dtd"> +<html><head><meta name="qrichtext" content="1" /><style type="text/css"> +p, li { white-space: pre-wrap; } +</style></head><body style=" font-family:'MS Shell Dlg 2'; font-size:8.25pt; font-weight:400; font-style:normal;"> +<p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;"><span style=" text-decoration: underline;">Warnings</span></p> +<p style="-qt-paragraph-type:empty; margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;"></p> +<p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;">These will define startup warnings.</p> +<p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;">Throttle warning - will alert if the throttle is not at idle during startup</p> +<p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;">Switch warning - will alert if switches are not in their defaul position</p> +<p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;">Memory warning - will alert if there's not a lot of memory left</p> +<p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;">Silent mode warning - will alert you if the beeper is set to quiet (0)</p></body></html> + + + + + + true + + + + + - T E R A + hh° (N/S) mm' ss''.dd - T E A R + NMEA + + + + + + + 0 + 0 + + + + + 0 + 22 + + + + + 16777215 + 16777215 + + + + <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0//EN" "http://www.w3.org/TR/REC-html40/strict.dtd"> +<html><head><meta name="qrichtext" content="1" /><style type="text/css"> +p, li { white-space: pre-wrap; } +</style></head><body style=" font-family:'MS Shell Dlg 2'; font-size:8.25pt; font-weight:400; font-style:normal;"> +<p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;"><span style=" text-decoration: underline;">Warnings</span></p> +<p style="-qt-paragraph-type:empty; margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;"></p> +<p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;">These will define startup warnings.</p> +<p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;">Throttle warning - will alert if the throttle is not at idle during startup</p> +<p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;">Switch warning - will alert if switches are not in their defaul position</p> +<p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;">Memory warning - will alert if there's not a lot of memory left</p> +<p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;">Silent mode warning - will alert you if the beeper is set to quiet (0)</p></body></html> + + + + + + true + + + + + - T A R E + 4800 Baud - T A E R + 9600 Baud - A R E T + 14400 Baud - A R T E + 19200 Baud - A E R T + 38400 Baud - A E T R + 57600 Baud - A T R E + 76800 Baud - A T E R + 115200 Baud - - - - Stick Mode - - - - - + + - - Metric - + + + + 0 + 0 + + + + + 16777215 + 16777215 + + + + Show splash screen on startup + + + Show splash screen on startup + + + + + - - Imperial - + + + + 0 + 0 + + + + + --- + + + + + 2s + + + + + 3s + + + + + 4s + + + + + 6s + + + + + 8s + + + + + 10s + + + + + 15s + + + - + - - + + - + 0 0 - - Default Channel Order - - - - - - - GPS Coordinates + + + 0 + 22 + - - - - @@ -1361,94 +1632,18 @@ - <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0//EN" "http://www.w3.org/TR/REC-html40/strict.dtd"> -<html><head><meta name="qrichtext" content="1" /><style type="text/css"> -p, li { white-space: pre-wrap; } -</style></head><body style=" font-family:'MS Shell Dlg 2'; font-size:8.25pt; font-weight:400; font-style:normal;"> -<p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;"><span style=" font-size:8pt;">LCD Screen Contrast</span></p> -<p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;"><span style=" font-size:8pt;">Values can be 20-45</span></p></body></html> + If not zero will sound beeps if the transmitter has been left without inputs for the specified number of minutes. - ms - - - 0 + min - 1000 - - - 10 - - - 0 + 120 - - - - - - Min - - - - - - - v - - - 1 - - - 4.000000000000000 - - - 16.000000000000000 - - - 0.100000000000000 - - - 9.000000000000000 - - - - - - - Max - - - - - - - v - - - 1 - - - 4.000000000000000 - - - 16.000000000000000 - - - 0.100000000000000 - - - 12.000000000000000 - - - - - - - + + 0 @@ -1458,16 +1653,23 @@ 0 - 0 + 22 - - Low Memory Warning - + + + Standard + + + + + Optrex + + - - + + 0 @@ -1477,16 +1679,46 @@ 0 - 0 + 22 - - Inactivity Timer + + + + + + + + Battery warning voltage. +This is the threashhold where the battery warning sounds. + +Acceptable values are 5v..10v + + + + + + V + + + 1 + + + 4.000000000000000 + + + 12.000000000000000 + + + 0.100000000000000 + + + 9.600000000000000 - - + + 0 @@ -1496,18 +1728,33 @@ 0 - 0 + 22 - - Show Splash Screen on Startup + + + + + + + + + + + 10 + + + 45 + + + 25 - - + + - + 0 0 @@ -1515,19 +1762,25 @@ 0 - 0 + 22 - - + + -2 - - Contrast + + 2 + + + 1 + + + Qt::Horizontal - - + + 0 @@ -1537,16 +1790,46 @@ 0 + 22 + + + + + Quiet + + + + + Only Alarms + + + + + No Keys + + + + + All + + + + + + + + + 0 0 - Battery Meter Range + MAVLink Baud Rate - - + + 0 @@ -1560,12 +1843,12 @@ - Haptic Strength + Haptic Length - - + + 0 @@ -1574,12 +1857,15 @@ - 0 + 20 0 + + + - LCD Display Type + Battery Warning @@ -1602,8 +1888,8 @@ - - + + 0 @@ -1612,20 +1898,17 @@ - 20 + 0 0 - - - - Battery Warning + LCD Display Type - - + + 0 @@ -1639,12 +1922,18 @@ - Haptic Length + Haptic Strength - - + + + + + 0 + 0 + + 0 @@ -1652,12 +1941,12 @@ - MAVLink Baud Rate + Battery Meter Range - - + + 0 @@ -1667,35 +1956,21 @@ 0 - 22 + 0 - - - Quiet - - - - - Only Alarms - - - - - No Keys - - - - - All - - + + + + + Contrast + - - + + - + 0 0 @@ -1703,25 +1978,16 @@ 0 - 22 + 0 - - -2 - - - 2 - - - 1 - - - Qt::Horizontal + + Show Splash Screen on Startup - - + + 0 @@ -1731,31 +1997,16 @@ 0 - 22 + 0 - - - - - - - - - - - 10 - - - 45 - - - 25 + + Low EEPROM Warning - - + + 0 @@ -1765,9 +2016,78 @@ 0 - 22 + 0 + + Inactivity Timer + + + + + + + + + Min + + + + + + + v + + + 1 + + + 4.000000000000000 + + + 16.000000000000000 + + + 0.100000000000000 + + + 9.000000000000000 + + + + + + + Max + + + + + + + v + + + 1 + + + 4.000000000000000 + + + 16.000000000000000 + + + 0.100000000000000 + + + 12.000000000000000 + + + + + + + @@ -1775,74 +2095,73 @@ - Battery warning voltage. -This is the threashhold where the battery warning sounds. - -Acceptable values are 5v..10v - - - + <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0//EN" "http://www.w3.org/TR/REC-html40/strict.dtd"> +<html><head><meta name="qrichtext" content="1" /><style type="text/css"> +p, li { white-space: pre-wrap; } +</style></head><body style=" font-family:'MS Shell Dlg 2'; font-size:8.25pt; font-weight:400; font-style:normal;"> +<p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;"><span style=" font-size:8pt;">LCD Screen Contrast</span></p> +<p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;"><span style=" font-size:8pt;">Values can be 20-45</span></p></body></html> - V - - - 1 + ms - 4.000000000000000 + 0 - 12.000000000000000 + 1000 - 0.100000000000000 + 10 - 9.600000000000000 + 0 - - + + + + GPS Coordinates + + + + + - + 0 0 - - - 0 - 22 - + + Default Channel Order + + + + - Standard + Metric - Optrex + Imperial - - - - - 0 - 0 - - - - - 0 - 22 - + + + + Stick Mode + + + + @@ -1850,374 +2169,135 @@ - If not zero will sound beeps if the transmitter has been left without inputs for the specified number of minutes. - - - min + <html><head/><body><p>Channel order</p><p><br/></p><p>Defines the order of the default mixes created on a new model.</p></body></html> - - 120 + + 0 - - - - - - - - - 0 - 0 - - - - - 16777215 - 16777215 - - - - Show splash screen on startup - - - Show splash screen on startup - - - - - - - - - - - 0 - 0 - - - - - --- - - - - - 2s - - - - - 3s - - - - - 4s - - - - - 6s - - - - - 8s - - - - - 10s - - - - - 15s - - - - - - - - - - - 4800 Baud - - - - - 9600 Baud - - - 14400 Baud - - - - - 19200 Baud - - - - - 38400 Baud - - - - - 57600 Baud + R E T A - 76800 Baud + R E A T - 115200 Baud - - - - - - - - - 0 - 0 - - - - - 0 - 22 - - - - - 16777215 - 16777215 - - - - <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0//EN" "http://www.w3.org/TR/REC-html40/strict.dtd"> -<html><head><meta name="qrichtext" content="1" /><style type="text/css"> -p, li { white-space: pre-wrap; } -</style></head><body style=" font-family:'MS Shell Dlg 2'; font-size:8.25pt; font-weight:400; font-style:normal;"> -<p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;"><span style=" text-decoration: underline;">Warnings</span></p> -<p style="-qt-paragraph-type:empty; margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;"></p> -<p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;">These will define startup warnings.</p> -<p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;">Throttle warning - will alert if the throttle is not at idle during startup</p> -<p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;">Switch warning - will alert if switches are not in their defaul position</p> -<p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;">Memory warning - will alert if there's not a lot of memory left</p> -<p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;">Silent mode warning - will alert you if the beeper is set to quiet (0)</p></body></html> - - - - - - true - - - - - - - - 0 - 0 - - - - - 16777215 - 16777215 - - - - <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0//EN" "http://www.w3.org/TR/REC-html40/strict.dtd"> -<html><head><meta name="qrichtext" content="1" /><style type="text/css"> -p, li { white-space: pre-wrap; } -</style></head><body style=" font-family:'MS Shell Dlg 2'; font-size:8.25pt; font-weight:400; font-style:normal;"> -<p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;"><span style=" text-decoration: underline;">Warnings</span></p> -<p style="-qt-paragraph-type:empty; margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;"></p> -<p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;">These will define startup warnings.</p> -<p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;">Throttle warning - will alert if the throttle is not at idle during startup</p> -<p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;">Switch warning - will alert if switches are not in their defaul position</p> -<p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;">Memory warning - will alert if there's not a lot of memory left</p> -<p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;">Silent mode warning - will alert you if the beeper is set to quiet (0)</p></body></html> - - - - - - true - - - - - - - - 0 - 0 - - - - - 0 - 22 - - + R T E A + + - X-Short + R T A E - Short + R A E T - Normal + R A T E - Long + E R T A - X-Long + E R A T - - - - - hh° (N/S) mm' ss''.dd + E T R A - NMEA + E T A R + + + + + E A R T + + + + + E A T R + + + + + T R E A + + + + + T R A E + + + + + T E R A + + + + + T E A R + + + + + T A R E + + + + + T A E R + + + + + A R E T + + + + + A R T E + + + + + A E R T + + + + + A E T R + + + + + A T R E + + + + + A T E R - - - - - 0 - 0 - - - - Play Delay (switch mid position) - - - - - - - Measurement Units - - - - - - - Qt::Vertical - - - - 20 - 40 - - - - - - - - - 0 - 0 - - - - - 0 - 0 - - - - Haptic Mode - - - - - - - - 0 - 0 - - - - - 0 - 0 - - - - Beeper Length - - - - - - - - 0 - 0 - - - - - 0 - 0 - - - - Beeper Mode - - - - - - - - 0 - 0 - - - - - 0 - 22 - - + + @@ -2225,73 +2305,78 @@ - Beeper volume + Mode selection: -0 - Quiet. No beeps at all. -1 - No Keys. Normal beeps but menu keys do not beep. -2 - Normal. -3 - Loud. -4 - Extra loud. +Mode 1: + Left stick: Elevator, Rudder + Right stick: Throttle, Aileron + +Mode 2: + Left stick: Throttle, Rudder + Right stick: Elevator, Aileron + +Mode 3: + Left stick: Elevator, Aileron + Right stick: Throttle, Rudder + +Mode 4: + Left stick: Throttle, Aileron + Right stick: Elevator, Rudder + + + + + 1 - Quiet + Mode 1 (RUD ELE THR AIL) - Alarms Only + Mode 2 (RUD THR ELE AIL) - No Keys + Mode 3 (AIL ELE THR RUD) - All + Mode 4 (AIL THR ELE RUD) - - - - - 0 - 0 - - - - - 0 - 22 - + + + + USB Mode + + + + - X-Short - - - - - Short + Ask on Connect - Normal + Joystick (HID) - Long + USB Mass Storage - X-Long + USB Serial (CDC) diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/helpers.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/helpers.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/helpers.cpp 2017-04-29 16:57:04.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/helpers.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -404,84 +404,6 @@ } } -void Helpers::addRawSwitchItems(QStandardItemModel * itemModel, const RawSwitchType & type, int count, const GeneralSettings * const generalSettings) -{ - // Most RawSwitch() indices are one-based (vs. typical zero); these are exceptions to the rule: - const static QVector rawSwitchIndexBaseZeroTypes = QVector() << SWITCH_TYPE_NONE << SWITCH_TYPE_ON << SWITCH_TYPE_OFF << SWITCH_TYPE_TIMER_MODE; - - int rawIdxAdj = 0; - const Board::Type board = getCurrentBoard(); - int i = (count < 0 ? count : 1); - const int maxCount = (i < 0 ? 0 : count + i); - - // handle exceptions in RawSwitch() index values - if (rawSwitchIndexBaseZeroTypes.contains(type)) - rawIdxAdj = -1; - - for ( ; i < maxCount; ++i) { - if (generalSettings) { - if (type == SWITCH_TYPE_SWITCH && IS_HORUS_OR_TARANIS(board) && !generalSettings->switchPositionAllowedTaranis(abs(i))) - continue; - if (type == SWITCH_TYPE_MULTIPOS_POT) { - int pot = div(abs(i) - 1, getCurrentFirmware()->getCapability(MultiposPotsPositions)).quot; - if (!generalSettings->isPotAvailable(pot) || generalSettings->potConfig[pot] != Board::POT_MULTIPOS_SWITCH) - continue; - } - } - RawSwitch rs(type, i + rawIdxAdj); - QStandardItem * modelItem = new QStandardItem(rs.toString(board, generalSettings)); - modelItem->setData(rs.toValue(), Qt::UserRole); - itemModel->appendRow(modelItem); - } -} - -QStandardItemModel * Helpers::getRawSwitchItemModel(const GeneralSettings * const generalSettings, SwitchContext context) -{ - QStandardItemModel * itemModel = new QStandardItemModel(); - Boards board = Boards(getCurrentBoard()); - Board::Type btype = board.getBoardType(); - Firmware * fw = getCurrentFirmware(); - - // Descending switch direction: NOT (!) switches - - if (context != MixesContext && context != GlobalFunctionsContext && IS_ARM(btype)) { - addRawSwitchItems(itemModel, SWITCH_TYPE_FLIGHT_MODE, -fw->getCapability(FlightModes), generalSettings); - } - if (context != GlobalFunctionsContext) { - addRawSwitchItems(itemModel, SWITCH_TYPE_VIRTUAL, -fw->getCapability(LogicalSwitches), generalSettings); - } - addRawSwitchItems(itemModel, SWITCH_TYPE_ROTARY_ENCODER, -fw->getCapability(RotaryEncoders), generalSettings); - addRawSwitchItems(itemModel, SWITCH_TYPE_TRIM, -board.getCapability(Board::NumTrimSwitches), generalSettings); - addRawSwitchItems(itemModel, SWITCH_TYPE_MULTIPOS_POT, -(fw->getCapability(MultiposPots) * fw->getCapability(MultiposPotsPositions)), generalSettings); - addRawSwitchItems(itemModel, SWITCH_TYPE_SWITCH, -board.getCapability(Board::SwitchPositions), generalSettings); - - // Ascending switch direction (including zero) - - if (context == TimersContext) { - addRawSwitchItems(itemModel, SWITCH_TYPE_TIMER_MODE, 5, generalSettings); - } - else { - addRawSwitchItems(itemModel, SWITCH_TYPE_NONE, 1); - } - - addRawSwitchItems(itemModel, SWITCH_TYPE_SWITCH, board.getCapability(Board::SwitchPositions), generalSettings); - addRawSwitchItems(itemModel, SWITCH_TYPE_MULTIPOS_POT, fw->getCapability(MultiposPots) * fw->getCapability(MultiposPotsPositions), generalSettings); - addRawSwitchItems(itemModel, SWITCH_TYPE_TRIM, board.getCapability(Board::NumTrimSwitches), generalSettings); - addRawSwitchItems(itemModel, SWITCH_TYPE_ROTARY_ENCODER, fw->getCapability(RotaryEncoders), generalSettings); - if (context != GlobalFunctionsContext) { - addRawSwitchItems(itemModel, SWITCH_TYPE_VIRTUAL, fw->getCapability(LogicalSwitches), generalSettings); - } - if (context != MixesContext && context != GlobalFunctionsContext && IS_ARM(btype)) { - addRawSwitchItems(itemModel, SWITCH_TYPE_FLIGHT_MODE, fw->getCapability(FlightModes), generalSettings); - } - if (context == SpecialFunctionsContext || context == GlobalFunctionsContext) { - addRawSwitchItems(itemModel, SWITCH_TYPE_ON, 1); - addRawSwitchItems(itemModel, SWITCH_TYPE_ONE, 1); - } - - return itemModel; -} - void Helpers::addRawSourceItems(QStandardItemModel * itemModel, const RawSourceType & type, int count, const GeneralSettings * const generalSettings, const ModelData * const model, const int start, const QList exclude) { @@ -778,10 +700,19 @@ int version2index(const QString & version) { int result = 999; - QStringList parts = version.split("N"); - if (parts.size() > 1) - result = parts[1].toInt(); // nightly build - parts = parts[0].split('.'); + QStringList parts; + QString mainVersion = version; + if (version.contains("RC")) { + parts = version.split("RC"); + result = parts[1].toInt() + 900; // RC0 = 900; RC1=901,.. + mainVersion = parts[0]; + } + else if (version.contains("N")) { + parts = version.split("N"); + result = parts[1].toInt(); // nightly build up to 899 + mainVersion = parts[0]; + } + parts = mainVersion.split('.'); if (parts.size() > 2) result += 1000 * parts[2].toInt(); if (parts.size() > 1) @@ -803,9 +734,12 @@ int minor = index % 100; int major = index / 100; result = templt.arg(major).arg(minor).arg(revision); - if (nightly > 0 && nightly < 999) { + if (nightly > 0 && nightly < 900) { result += "N" + QString::number(nightly); } + else if (nightly >= 900 && nightly < 1000) { + result += "RC" + QString::number(nightly-900); + } } else if (index >= 19900) { int revision = index % 100; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/helpers.h opentx-companion22-2.2.1~ppa01~xenial/companion/src/helpers.h --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/helpers.h 2017-04-29 16:57:04.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/helpers.h 2017-10-31 16:16:43.000000000 +0000 @@ -129,18 +129,6 @@ namespace Helpers { - enum SwitchContext - { - LogicalSwitchesContext, - SpecialFunctionsContext, - GlobalFunctionsContext, - TimersContext, - MixesContext - }; - - void addRawSwitchItems(QStandardItemModel * itemModel, const RawSwitchType & type, int count, const GeneralSettings * const generalSettings = NULL); - QStandardItemModel * getRawSwitchItemModel(const GeneralSettings * const generalSettings = NULL, SwitchContext context = LogicalSwitchesContext); - void addRawSourceItems(QStandardItemModel * itemModel, const RawSourceType & type, int count, const GeneralSettings * const generalSettings = NULL, const ModelData * const model = NULL, const int start = 0, const QList exclude = QList()); QStandardItemModel * getRawSourceItemModel(const GeneralSettings * const generalSettings = NULL, const ModelData * const model = NULL, unsigned int flags = 0); Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/Horus/border-right.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/Horus/border-right.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/Horus/bottom.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/Horus/bottom.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/Horus/led.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/Horus/led.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/Horus/left_btn1.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/Horus/left_btn1.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/Horus/left_btn2.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/Horus/left_btn2.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/Horus/left.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/Horus/left.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/Horus/left_scrnsht.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/Horus/left_scrnsht.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/Horus/middle.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/Horus/middle.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/Horus/right_btnD.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/Horus/right_btnD.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/Horus/right_btnL.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/Horus/right_btnL.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/Horus/right_btnR.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/Horus/right_btnR.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/Horus/right_btnU.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/Horus/right_btnU.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/Horus/right_ent.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/Horus/right_ent.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/Horus/right.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/Horus/right.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/Horus/right_re_ph2.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/Horus/right_re_ph2.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/Horus/right_re_ph3.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/Horus/right_re_ph3.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/Horus/top.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/Horus/top.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/X10/bottom.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/X10/bottom.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/X10/left_mdl.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/X10/left_mdl.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/X10/left_page.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/X10/left_page.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/X10/left.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/X10/left.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/X10/left_rtn.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/X10/left_rtn.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/X10/left_scrnsht.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/X10/left_scrnsht.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/X10/left_sys.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/X10/left_sys.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/X10/left_tele.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/X10/left_tele.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/X10/right_ent.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/X10/right_ent.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/X10/right.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/X10/right.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/X10/top.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/X10/top.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/X12/border-right.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/X12/border-right.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/X12/bottom.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/X12/bottom.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/X12/led.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/X12/led.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/X12/left_btn1.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/X12/left_btn1.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/X12/left_btn2.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/X12/left_btn2.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/X12/left.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/X12/left.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/X12/left_scrnsht.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/X12/left_scrnsht.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/X12/middle.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/X12/middle.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/X12/right_btnD.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/X12/right_btnD.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/X12/right_btnL.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/X12/right_btnL.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/X12/right_btnR.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/X12/right_btnR.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/X12/right_btnU.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/X12/right_btnU.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/X12/right_ent.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/X12/right_ent.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/X12/right.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/X12/right.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/companion/src/images/simulator/X12/top.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/companion/src/images/simulator/X12/top.png differ diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/logsdialog.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/logsdialog.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/logsdialog.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/logsdialog.cpp 2017-11-20 18:44:06.000000000 +0000 @@ -100,6 +100,8 @@ ui->mapsButton->hide(); } + ui->SaveSession_PB->setEnabled(false); + // connect slot that ties some axis selections together (especially opposite axes): connect(ui->customPlot, SIGNAL(selectionChangedByUser()), this, SLOT(selectionChanged())); // connect slots that takes care that when an axis is selected, only that direction can be dragged and zoomed: @@ -116,6 +118,7 @@ connect(ui->FieldsTW, SIGNAL(itemSelectionChanged()), this, SLOT(plotLogs())); connect(ui->logTable, SIGNAL(itemSelectionChanged()), this, SLOT(plotLogs())); connect(ui->Reset_PB, SIGNAL(clicked()), this, SLOT(plotLogs())); + connect(ui->SaveSession_PB, SIGNAL(clicked()), this, SLOT(on_saveSession_BT_clicked())); } LogsDialog::~LogsDialog() @@ -610,6 +613,48 @@ } } +void LogsDialog::on_saveSession_BT_clicked() +{ + int index = ui->sessions_CB->currentIndex(); + // ignore index 0 is its all sessions combined + if(index > 0) { + int n = csvlog.count(); + QList sessionCsvLog; + // add CSV headers from first row of source file + sessionCsvLog.push_back(csvlog[0]); + // find session breaks + int currentSession = 0; + QDateTime lastvalue; + for (int i = 1; i < n; i++) { + QDateTime tmp = getRecordTimeStamp(i); + if (!lastvalue.isValid() || lastvalue.secsTo(tmp) > 60) { + currentSession++; + } + lastvalue = tmp; + if(currentSession == index) { + // add records to filtered list + sessionCsvLog.push_back(csvlog[i]); + } + else if (currentSession > index) { + break; + } + } + // save the filtered records to a new file + QString newFilename = logFilename; + newFilename.append(QString("-Session%1.csv").arg(index)); + QString filename = QFileDialog::getSaveFileName(this, "Save log", newFilename, "CSV files (.csv);", 0, 0); // getting the filename (full path) + QFile data(filename); + if(data.open(QFile::WriteOnly |QFile::Truncate)) { + QTextStream output(&data); + int numRecords = sessionCsvLog.count(); + for(int i = 0; i < numRecords; i++){ + output << sessionCsvLog[i].join(",") << '\n'; + } + } + sessionCsvLog.clear(); + } +} + bool LogsDialog::cvsFileParse() { QFile file(ui->FileName_LE->text()); @@ -697,6 +742,7 @@ void LogsDialog::setFlightSessions() { ui->sessions_CB->clear(); + ui->SaveSession_PB->setEnabled(false); int n = csvlog.count(); // qDebug() << "records" << n; @@ -756,6 +802,11 @@ QItemSelection selection(topLeft, bottomRight); ui->logTable->selectionModel()->select(selection, QItemSelectionModel::Select); + + ui->SaveSession_PB->setEnabled(true); + } + else { + ui->SaveSession_PB->setEnabled(false); } plotLock = false; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/logsdialog.h opentx-companion22-2.2.1~ppa01~xenial/companion/src/logsdialog.h --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/logsdialog.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/logsdialog.h 2017-11-20 18:44:06.000000000 +0000 @@ -78,6 +78,7 @@ void removeAllGraphs(); void plotLogs(); void on_fileOpen_BT_clicked(); + void on_saveSession_BT_clicked(); void on_sessions_CB_currentIndexChanged(int index); void on_mapsButton_clicked(); void yAxisChangeRanges(QCPRange range); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/logsdialog.ui opentx-companion22-2.2.1~ppa01~xenial/companion/src/logsdialog.ui --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/logsdialog.ui 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/logsdialog.ui 2017-11-20 18:44:06.000000000 +0000 @@ -37,6 +37,13 @@ + + + Save session CSV + + + + Qt::Horizontal diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/mainwindow.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/mainwindow.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/mainwindow.cpp 2017-05-31 19:49:19.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/mainwindow.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -54,7 +54,6 @@ #include #define OPENTX_DOWNLOADS_PAGE_URL "http://www.open-tx.org/downloads" -#define OPENTX_COMPANION_DOWNLOADS "http://downloads-22.open-tx.org/companion" #define DONATE_STR "https://www.paypal.com/cgi-bin/webscr?cmd=_s-xclick&hosted_button_id=QUZ48K4SEXDP2" #ifdef __APPLE__ @@ -69,12 +68,16 @@ #define COMPANION_INSTALL_QUESTION tr("Would you like to launch the installer?") #else #define COMPANION_STAMP "companion-linux.stamp" - #define COMPANION_INSTALLER "" // no automatated updates for linux + #define COMPANION_INSTALLER "" // no automated updates for linux #define COMPANION_FILEMASK "*.*" #define COMPANION_INSTALL_QUESTION tr("Would you like to launch the installer?") #endif -#define OPENTX_NIGHT_COMPANION_DOWNLOADS "http://downloads-22.open-tx.org/nightlies/companion" +const char * const OPENTX_COMPANION_DOWNLOAD_URL[] = { + "https://downloads.open-tx.org/2.2/release/companion", + "https://downloads.open-tx.org/2.2/rc/companion", + "https://downloads.open-tx.org/2.2/nightlies/companion" +}; MainWindow::MainWindow(): downloadDialog_forWait(NULL), @@ -241,11 +244,7 @@ QString MainWindow::getCompanionUpdateBaseUrl() { -#if defined(ALLOW_NIGHTLY_BUILDS) - return g.useCompanionNightlyBuilds() ? OPENTX_NIGHT_COMPANION_DOWNLOADS : OPENTX_COMPANION_DOWNLOADS; -#else - return OPENTX_COMPANION_DOWNLOADS; -#endif + return OPENTX_COMPANION_DOWNLOAD_URL[g.boundedOpenTxBranch()]; } void MainWindow::checkForUpdates() @@ -562,6 +561,7 @@ g.mainWinGeo(saveGeometry()); g.mainWinState(saveState()); g.tabbedMdi(actTabbedWindows->isChecked()); + QApplication::closeAllWindows(); mdiArea->closeAllSubWindows(); if (mdiArea->currentSubWindow()) { event->ignore(); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/mdichild.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/mdichild.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/mdichild.cpp 2017-05-14 17:18:57.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/mdichild.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -1414,11 +1414,11 @@ isUntitled = false; setWindowModified(false); updateTitle(); - int MaxRecentFiles = g.historySize(); + QStringList files = g.recentFiles(); - files.removeAll(fileName); - files.prepend(fileName); - while (files.size() > MaxRecentFiles) + files.removeAll(curFile); + files.prepend(curFile); + while (files.size() > g.historySize()) files.removeLast(); g.recentFiles(files); } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/checklistdialog.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/checklistdialog.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/checklistdialog.cpp 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/checklistdialog.cpp 2017-11-15 20:54:40.000000000 +0000 @@ -0,0 +1,118 @@ +/* + * Copyright (C) OpenTX + * + * Based on code named + * th9x - http://code.google.com/p/th9x + * er9x - http://code.google.com/p/er9x + * gruvin9x - http://code.google.com/p/gruvin9x + * + * License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + * + * 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. + */ + +#include "checklistdialog.h" +#include "ui_checklistdialog.h" + +#include "appdata.h" +#include "helpers.h" + +#include +#include + +extern AppData g; + +ChecklistDialog::ChecklistDialog(QWidget *parent, const QString modelName): + QDialog(parent), + ui(new Ui::ChecklistDialog), + mDirty(false) +{ + ui->setupUi(this); + setWindowIcon(CompanionIcon("edit.png")); + + mChecklistFolder = g.profile[g.id()].sdPath() + "/MODELS/"; + QString name = modelName; + name.replace(" ", "_"); + mModelChecklist = QDir::toNativeSeparators(mChecklistFolder + name + ".txt"); + ui->file->setText("File: " + mModelChecklist); + ui->pteCheck->setPlainText(readFile(mModelChecklist,QFile::exists(mModelChecklist))); + + connect(ui->pteCheck, SIGNAL(textChanged()), this, SLOT(changed())); + connect(ui->pbImport, SIGNAL(clicked()), this, SLOT(import())); + connect(ui->pbCancel, SIGNAL(clicked()), this, SLOT(reject())); + connect(ui->pbOK, SIGNAL(clicked()), this, SLOT(update())); +} + +ChecklistDialog::~ChecklistDialog() +{ + delete ui; +} + +void ChecklistDialog::changed() +{ + mDirty = true; +} + +void ChecklistDialog::import() +{ + QString filename = QFileDialog::getOpenFileName(this, tr("Open Checklist"), mChecklistFolder, tr("Checklist Files (*.txt)")); + if (!filename.isNull()) + ui->pteCheck->setPlainText(readFile(filename,true)); + mDirty = true; +} + +void ChecklistDialog::update() +{ + if (mDirty) { + QFile file(mModelChecklist); + if (!file.open(QFile::WriteOnly | QFile::Text)) { + QMessageBox::critical(this, tr("Model Checklist"), tr("Cannot open file for writing %1:\n%2.").arg(mModelChecklist, file.errorString())); + } + else { + QTextStream out(&file); + if (out.status()==QTextStream::Ok) { + out << ui->pteCheck->toPlainText(); + if (!(out.status()==QTextStream::Ok)) { + QMessageBox::critical(this, tr("Model Checklist"), tr("Cannot write to file %1:\n%2.").arg(mModelChecklist, file.errorString())); + if (!file.flush()) { + QMessageBox::critical(this, tr("Model Checklist"), tr("Cannot write file %1:\n%2.").arg(mModelChecklist, file.errorString())); + } + } + } + } + file.close(); + } + emit accept(); +} + +QString ChecklistDialog::readFile(const QString & filepath, const bool exists) +{ + QString data = ""; + if (!filepath.isNull()) { + QFile file(filepath); + if (!file.open(QFile::ReadOnly | QFile::Text)) { + if (exists) { + QMessageBox::critical(this, tr("Model Checklist"), tr("Cannot open file %1:\n%2.").arg(QDir::toNativeSeparators(filepath), file.errorString())); + } + } + else { + QTextStream in(&file); + if (in.status()==QTextStream::Ok) { + data = in.readAll(); + if (!(in.status()==QTextStream::Ok)) { + QMessageBox::critical(this, tr("Model Checklist"), tr("Cannot read file %1:\n%2.").arg(QDir::toNativeSeparators(filepath), file.errorString())); + data = ""; + } + } + } + file.close(); + } + return data; +} diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/checklistdialog.h opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/checklistdialog.h --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/checklistdialog.h 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/checklistdialog.h 2017-10-31 16:16:43.000000000 +0000 @@ -0,0 +1,50 @@ +/* + * Copyright (C) OpenTX + * + * Based on code named + * th9x - http://code.google.com/p/th9x + * er9x - http://code.google.com/p/er9x + * gruvin9x - http://code.google.com/p/gruvin9x + * + * License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + * + * 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. + */ + +#ifndef _CHECKLISTDIALOG_H_ +#define _CHECKLISTDIALOG_H_ + +#include + +namespace Ui { + class ChecklistDialog; +} + +class ChecklistDialog : public QDialog { + Q_OBJECT + +public: + ChecklistDialog(QWidget *parent, const QString modelName); + ~ChecklistDialog(); + +private slots: + void import(); + void update(); + void changed(); + +private: + Ui::ChecklistDialog *ui; + QString mModelChecklist; + QString mChecklistFolder; + QString readFile(const QString & filepath, const bool exists); + bool mDirty; +}; + +#endif // _CHECKLISTDIALOG_H_ diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/checklistdialog.ui opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/checklistdialog.ui --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/checklistdialog.ui 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/checklistdialog.ui 2017-10-31 16:16:43.000000000 +0000 @@ -0,0 +1,156 @@ + + + ChecklistDialog + + + + 0 + 0 + 630 + 373 + + + + Edit Checklist + + + + + + Qt::Vertical + + + QSizePolicy::Fixed + + + + 20 + 3 + + + + + + + + + 0 + 1 + + + + Qt::ScrollBarAsNeeded + + + Qt::ScrollBarAsNeeded + + + true + + + QPlainTextEdit::NoWrap + + + + + + + 6 + + + QLayout::SetMinimumSize + + + + + Qt::Horizontal + + + QSizePolicy::Expanding + + + + 40 + 20 + + + + + + + + + 0 + 0 + + + + &Import... + + + + + + + + 0 + 0 + + + + &Cancel + + + + + + + + 0 + 0 + + + + &OK + + + + + + false + + + + + + + + + Please note, the maximum width displayable is radio model limited. Also, renaming the model will break the link to this checklist file. + + + true + + + + + + + File: unknown + + + true + + + + + + + pteCheck + pbOK + pbCancel + pbImport + + + + diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/CMakeLists.txt opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/CMakeLists.txt --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/CMakeLists.txt 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/CMakeLists.txt 2017-10-31 16:16:43.000000000 +0000 @@ -12,9 +12,11 @@ telemetry expodialog mixerdialog + checklistdialog ) set(modeledit_SRCS + switchitemmodel.cpp flightmodes.cpp inputs.cpp mixes.cpp diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/curves.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/curves.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/curves.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/curves.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -143,8 +143,10 @@ palette.setBrush(QPalette::Active, QPalette::ButtonText, QBrush(Qt::white)); #ifdef __APPLE__ edit->setStyleSheet(QString("color: %1;").arg(colors[i].name())); -#else +#elif defined WIN32 || !defined __GNUC__ edit->setStyleSheet(QString("background-color: %1; color: white;").arg(colors[i].name())); +#else + edit->setStyleSheet(QString("background-color: %1; color: white; padding: 2px 3px; border-style: outset; border-width: 1px; border-radius: 2px; border-color: inherit;").arg(colors[i].name())); #endif edit->setPalette(palette); edit->setText(tr("Curve %1").arg(i+1)); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/customfunctions.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/customfunctions.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/customfunctions.cpp 2017-04-29 16:57:04.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/customfunctions.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -19,6 +19,7 @@ */ #include "customfunctions.h" +#include "switchitemmodel.h" #include "helpers.h" #include "appdata.h" @@ -73,8 +74,7 @@ lock = true; int num_fsw = model ? firmware->getCapability(CustomFunctions) : firmware->getCapability(GlobalFunctions); - rawSwitchItemModel = Helpers::getRawSwitchItemModel(&generalSettings, model ? Helpers::SpecialFunctionsContext : Helpers::GlobalFunctionsContext); - rawSwitchItemModel->setParent(this); + rawSwitchItemModel = new RawSwitchFilterItemModel(&generalSettings, model, model ? SpecialFunctionsContext : GlobalFunctionsContext); rawSrcInputsItemModel = Helpers::getRawSourceItemModel(&generalSettings, model, POPULATE_NONE|POPULATE_SOURCES|POPULATE_VIRTUAL_INPUTS|POPULATE_TRIMS|POPULATE_SWITCHES); rawSrcInputsItemModel->setParent(this); rawSrcAllItemModel = Helpers::getRawSourceItemModel(&generalSettings, model, POPULATE_NONE|POPULATE_SOURCES|POPULATE_VIRTUAL_INPUTS|POPULATE_SWITCHES|POPULATE_GVARS|POPULATE_TRIMS|POPULATE_TELEMETRY|POPULATE_TELEMETRYEXT|POPULATE_SCRIPT_OUTPUTS); @@ -411,23 +411,28 @@ widgetsMask |= CUSTOM_FUNCTION_NUMERIC_PARAM; } else if (func>=FuncAdjustGV1 && func<=FuncAdjustGVLast) { + int gvidx = func - FuncAdjustGV1; if (modified) cfn.adjustMode = fswtchGVmode[i]->currentIndex(); widgetsMask |= CUSTOM_FUNCTION_GV_MODE | CUSTOM_FUNCTION_ENABLE; if (cfn.adjustMode==FUNC_ADJUST_GVAR_CONSTANT || cfn.adjustMode==FUNC_ADJUST_GVAR_INCDEC) { if (modified) - cfn.param = fswtchParam[i]->value(); - fswtchParam[i]->setDecimals(0); - fswtchParam[i]->setSingleStep(1); + cfn.param = fswtchParam[i]->value() * model->gvarData[gvidx].multiplierSet(); if (IS_ARM(getCurrentBoard())) { - fswtchParam[i]->setMinimum(-500); - fswtchParam[i]->setMaximum(500); + fswtchParam[i]->setDecimals(model->gvarData[gvidx].prec); + fswtchParam[i]->setSingleStep(model->gvarData[gvidx].multiplierGet()); + fswtchParam[i]->setSuffix(model->gvarData[gvidx].unitToString()); + fswtchParam[i]->setMinimum(model->gvarData[gvidx].getMinPrec()); + fswtchParam[i]->setMaximum(model->gvarData[gvidx].getMaxPrec()); + fswtchParam[i]->setValue(cfn.param * model->gvarData[gvidx].multiplierGet()); } else { + fswtchParam[i]->setDecimals(0); + fswtchParam[i]->setSingleStep(1); fswtchParam[i]->setMinimum(-125); fswtchParam[i]->setMaximum(125); + fswtchParam[i]->setValue(cfn.param); } - fswtchParam[i]->setValue(cfn.param); widgetsMask |= CUSTOM_FUNCTION_NUMERIC_PARAM; } else { @@ -584,6 +589,8 @@ void CustomFunctionsPanel::update() { + rawSwitchItemModel->update(); + lock = true; int num_fsw = model ? firmware->getCapability(CustomFunctions) : firmware->getCapability(GlobalFunctions); for (int i=0; ihasFormat("application/x-companion-fsw"); QMenu contextMenu; - contextMenu.addAction(CompanionIcon("copy.png"), tr("&Copy"),this,SLOT(fswCopy()),tr("Ctrl+C")); - contextMenu.addAction(CompanionIcon("cut.png"), tr("&Cut"),this,SLOT(fswCut()),tr("Ctrl+X")); - contextMenu.addAction(CompanionIcon("paste.png"), tr("&Paste"),this,SLOT(fswPaste()),tr("Ctrl+V"))->setEnabled(hasData); - contextMenu.addAction(CompanionIcon("clear.png"), tr("&Delete"),this,SLOT(fswDelete()),tr("Delete")); + contextMenu.addAction(CompanionIcon("copy.png"), tr("&Copy"),this,SLOT(fswCopy())); + contextMenu.addAction(CompanionIcon("cut.png"), tr("&Cut"),this,SLOT(fswCut())); + contextMenu.addAction(CompanionIcon("paste.png"), tr("&Paste"),this,SLOT(fswPaste()))->setEnabled(hasData); + contextMenu.addAction(CompanionIcon("clear.png"), tr("&Delete"),this,SLOT(fswDelete())); contextMenu.exec(globalPos); } @@ -668,16 +675,14 @@ ((i==FuncPlayHaptic) && !firmware->getCapability(Haptic)) || ((i==FuncPlayBoth) && !firmware->getCapability(HasBeeper)) || ((i==FuncLogs) && !firmware->getCapability(HasSDLogs)) || + ((i==FuncSetTimer1 || i==FuncSetTimer2) && !IS_ARM(firmware->getBoard())) || ((i==FuncSetTimer3) && firmware->getCapability(Timers) < 3) || - ((i==FuncScreenshot) && IS_HORUS(firmware->getBoard())) || + ((i==FuncScreenshot) && !IS_TARANIS(firmware->getBoard())) || ((i>=FuncRangeCheckInternalModule && i<=FuncBindExternalModule) && (!model || !firmware->getCapability(DangerousFunctions))) || - ((i>=FuncAdjustGV1 && i<=FuncAdjustGVLast) && !firmware->getCapability(Gvars)) + ((i>=FuncAdjustGV1 && i<=FuncAdjustGVLast) && (!model || !firmware->getCapability(Gvars))) ) { // skipped - // b->addItem(CustomFunctionData(AssignFunc(i)).funcToString(), i); - // QModelIndex index = b->model()->index(i, 0); - // QVariant v(0); - // b->model()->setData(index, v, Qt::UserRole - 1); + continue; } else { b->addItem(CustomFunctionData(AssignFunc(i)).funcToString(model), i); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/customfunctions.h opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/customfunctions.h --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/customfunctions.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/customfunctions.h 2017-10-31 16:16:43.000000000 +0000 @@ -21,9 +21,11 @@ #ifndef _CUSTOMFUNCTIONS_H_ #define _CUSTOMFUNCTIONS_H_ +#include #include "modeledit.h" #include "eeprominterface.h" -#include + +class RawSwitchFilterItemModel; class RepeatComboBox: public QComboBox { @@ -74,7 +76,7 @@ void populateFuncCB(QComboBox *b, unsigned int value); void populateGVmodeCB(QComboBox *b, unsigned int value); void populateFuncParamCB(QComboBox *b, uint function, unsigned int value, unsigned int adjustmode=0); - QStandardItemModel * rawSwitchItemModel; + RawSwitchFilterItemModel * rawSwitchItemModel; QStandardItemModel * rawSrcInputsItemModel; QStandardItemModel * rawSrcAllItemModel; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/expodialog.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/expodialog.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/expodialog.cpp 2017-05-14 17:18:57.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/expodialog.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -20,6 +20,7 @@ #include "expodialog.h" #include "ui_expodialog.h" +#include "switchitemmodel.h" #include "helpers.h" ExpoDialog::ExpoDialog(QWidget *parent, ModelData & model, ExpoData *expoData, GeneralSettings & generalSettings, @@ -45,7 +46,7 @@ setWindowTitle(tr("Edit %1").arg(RawSource(srcType, ed->chn).toString(&model, &generalSettings))); QRegExp rx(CHAR_FOR_NAMES_REGEX); - if (IS_HORUS_OR_TARANIS(getCurrentBoard())) { + if (IS_ARM(getCurrentBoard())) { gvWeightGroup = new GVarGroup(ui->weightGV, ui->weightSB, ui->weightCB, ed->weight, model, 100, -100, 100); gvOffsetGroup = new GVarGroup(ui->offsetGV, ui->offsetSB, ui->offsetCB, ed->offset, model, 0, -100, 100); } @@ -61,7 +62,7 @@ curveGroup = new CurveGroup(ui->curveTypeCB, ui->curveGVarCB, ui->curveValueCB, ui->curveValueSB, ed->curve, model, firmware->getCapability(HasInputDiff) ? 0 : (HIDE_DIFF | HIDE_NEGATIVE_CURVES)); - ui->switchesCB->setModel(Helpers::getRawSwitchItemModel(&generalSettings, Helpers::MixesContext)); + ui->switchesCB->setModel(new RawSwitchFilterItemModel(&generalSettings, &model, MixesContext)); ui->switchesCB->setCurrentIndex(ui->switchesCB->findData(ed->swtch.toValue())); ui->sideCB->setCurrentIndex(ed->mode-1); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/flightmodes.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/flightmodes.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/flightmodes.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/flightmodes.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -20,7 +20,9 @@ #include "flightmodes.h" #include "ui_flightmode.h" +#include "switchitemmodel.h" #include "helpers.h" +#include "customdebug.h" FlightModePanel::FlightModePanel(QWidget * parent, ModelData & model, int phaseIdx, GeneralSettings & generalSettings, Firmware * firmware): ModelPanel(parent, model, generalSettings, firmware), @@ -28,7 +30,8 @@ phaseIdx(phaseIdx), phase(model.flightModeData[phaseIdx]), reCount(firmware->getCapability(RotaryEncoders)), - gvCount(firmware->getCapability(Gvars)) + gvCount(firmware->getCapability(Gvars)), + rawSwitchItemModel(NULL) { ui->setupUi(this); @@ -50,7 +53,8 @@ // Phase switch if (phaseIdx > 0) { - ui->swtch->setModel(Helpers::getRawSwitchItemModel(&generalSettings, Helpers::MixesContext)); + rawSwitchItemModel = new RawSwitchFilterItemModel(&generalSettings, &model, MixesContext); + ui->swtch->setModel(rawSwitchItemModel); ui->swtch->setCurrentIndex(ui->swtch->findData(phase.swtch.toValue())); connect(ui->swtch, SIGNAL(currentIndexChanged(int)), this, SLOT(phaseSwitch_currentIndexChanged(int))); } @@ -153,26 +157,56 @@ // GVars if (gvCount > 0 && (firmware->getCapability(GvarsFlightModes) || phaseIdx == 0) ) { QGridLayout *gvLayout = new QGridLayout(ui->gvGB); - + // Column headers int headerCol = 1; - QLabel *nameLabel = new QLabel(ui->gvGB); - nameLabel->setText(tr("Name")); - gvLayout->addWidget(nameLabel, 0, headerCol++, 1, 1); + + if (firmware->getCapability(GvarsName)) { + QLabel *nameLabel = new QLabel(ui->gvGB); + nameLabel->setText(tr("Name")); + gvLayout->addWidget(nameLabel, 0, headerCol++, 1, 1); + } + if (phaseIdx > 0) { QLabel *sourceLabel = new QLabel(ui->gvGB); sourceLabel->setText(tr("Value source")); gvLayout->addWidget(sourceLabel, 0, headerCol++, 1, 1); } + QLabel *valueLabel = new QLabel(ui->gvGB); valueLabel->setText(tr("Value")); gvLayout->addWidget(valueLabel, 0, headerCol++, 1, 1); - + + if (IS_HORUS_OR_TARANIS(board) && phaseIdx == 0) { + QLabel *unitLabel = new QLabel(ui->gvGB); + unitLabel->setText(tr("Unit")); + gvLayout->addWidget(unitLabel, 0, headerCol++, 1, 1); + + QLabel *precLabel = new QLabel(ui->gvGB); + precLabel->setText(tr("Prec")); + gvLayout->addWidget(precLabel, 0, headerCol++, 1, 1); + + QLabel *minLabel = new QLabel(ui->gvGB); + minLabel->setText(tr("Min")); + gvLayout->addWidget(minLabel, 0, headerCol++, 1, 1); + + QLabel *maxLabel = new QLabel(ui->gvGB); + maxLabel->setText(tr("Max")); + gvLayout->addWidget(maxLabel, 0, headerCol++, 1, 1); + + QLabel *popupLabel = new QLabel(ui->gvGB); + popupLabel->setText(tr("Popup enabled")); + gvLayout->addWidget(popupLabel, 0, headerCol++, 1, 1); + } + for (int i=0; igvGB); label->setText(tr("GVAR%1").arg(i+1)); + label->setProperty("index", i); + label->setContextMenuPolicy(Qt::CustomContextMenu); + connect(label, SIGNAL(customContextMenuRequested(const QPoint &)), this, SLOT(gvLabel_customContextMenuRequested(const QPoint &))); gvLayout->addWidget(label, i+1, col++, 1, 1); // GVar name int nameLen = firmware->getCapability(GvarsName); @@ -188,25 +222,49 @@ gvUse[i] = new QComboBox(ui->gvGB); gvUse[i]->setProperty("index", i); Helpers::populateGvarUseCB(gvUse[i], phaseIdx); - if (phase.gvars[i] > 1024) { - gvUse[i]->setCurrentIndex(phase.gvars[i] - 1024); + if (phase.gvars[i] > GVAR_MAX_VALUE) { + gvUse[i]->setCurrentIndex(phase.gvars[i] - GVAR_MAX_VALUE); } connect(gvUse[i], SIGNAL(currentIndexChanged(int)), this, SLOT(phaseGVUse_currentIndexChanged(int))); gvLayout->addWidget(gvUse[i], i+1, col++, 1, 1); } // GVar value - gvValues[i] = new QSpinBox(ui->gvGB); + gvValues[i] = new QDoubleSpinBox(ui->gvGB); gvValues[i]->setProperty("index", i); connect(gvValues[i], SIGNAL(editingFinished()), this, SLOT(phaseGVValue_editingFinished())); - gvValues[i]->setMinimum(-1024); - gvValues[i]->setMaximum(1024); gvLayout->addWidget(gvValues[i], i+1, col++, 1, 1); - // Popups - if (IS_TARANIS(board) && phaseIdx == 0) { + if (IS_HORUS_OR_TARANIS(board) && phaseIdx == 0) { + // GVar unit + gvUnit[i] = new QComboBox(ui->gvGB); + gvUnit[i]->setProperty("index", i); + populateGvarUnitCB(gvUnit[i]); + connect(gvUnit[i], SIGNAL(currentIndexChanged(int)), this, SLOT(phaseGVUnit_currentIndexChanged(int))); + gvLayout->addWidget(gvUnit[i], i+1, col++, 1, 1); + + // GVar precision + gvPrec[i] = new QComboBox(ui->gvGB); + gvPrec[i]->setProperty("index", i); + populateGvarPrecCB(gvPrec[i]); + connect(gvPrec[i], SIGNAL(currentIndexChanged(int)), this, SLOT(phaseGVPrec_currentIndexChanged(int))); + gvLayout->addWidget(gvPrec[i], i+1, col++, 1, 1); + + // GVar min + gvMin[i] = new QDoubleSpinBox(ui->gvGB); + gvMin[i]->setProperty("index", i); + connect(gvMin[i], SIGNAL(editingFinished()), this, SLOT(phaseGVMin_editingFinished())); + gvLayout->addWidget(gvMin[i], i+1, col++, 1, 1); + + // GVar max + gvMax[i] = new QDoubleSpinBox(ui->gvGB); + gvMax[i]->setProperty("index", i); + connect(gvMax[i], SIGNAL(editingFinished()), this, SLOT(phaseGVMax_editingFinished())); + gvLayout->addWidget(gvMax[i], i+1, col++, 1, 1); + + // Popups gvPopups[i] = new QCheckBox(ui->gvGB); gvPopups[i]->setProperty("index", i); - gvPopups[i]->setText(tr("Popup enabled")); + //gvPopups[i]->setText(tr("Popup enabled")); connect(gvPopups[i], SIGNAL(toggled(bool)), this, SLOT(phaseGVPopupToggled(bool))); gvLayout->addWidget(gvPopups[i], i+1, col++, 1, 1); } @@ -214,6 +272,7 @@ } else { ui->gvGB->hide(); + gvCount = 0; } disableMouseScrolling(); @@ -228,6 +287,10 @@ void FlightModePanel::update() { + if (rawSwitchItemModel) { + rawSwitchItemModel->update(); + } + ui->name->setText(phase.name); int scale = firmware->getCapability(SlowScale); @@ -247,17 +310,8 @@ trimUpdate(i); } - if (ui->gvGB->isVisible()) { - for (int i=0; igetCapability(GvarsName) > 0) { - gvNames[i]->setText(model->gvars_names[i]); - } - gvValues[i]->setDisabled(model->isGVarLinked(phaseIdx, i)); - gvValues[i]->setValue(model->getGVarFieldValue(phaseIdx, i)); - if (IS_TARANIS(getCurrentBoard()) && phaseIdx == 0) { - gvPopups[i]->setChecked(model->gvars_popups[i]); - } - } + for (int i=0; isetValue(phasere->rotaryEncoders[i]); } } +void FlightModePanel::updateGVar(int index) +{ + lock = true; + if (firmware->getCapability(GvarsName) > 0) { + gvNames[index]->setText(model->gvarData[index].name); + } + gvValues[index]->setDisabled(model->isGVarLinked(phaseIdx, index)); + setGVSB(gvValues[index], model->gvarData[index].getMin(), model->gvarData[index].getMax(), model->getGVarFieldValue(phaseIdx, index)); + if (IS_HORUS_OR_TARANIS(getCurrentBoard()) && phaseIdx == 0) { + gvUnit[index]->setCurrentIndex(model->gvarData[index].unit); + gvPrec[index]->setCurrentIndex(model->gvarData[index].prec); + setGVSB(gvMin[index], GVAR_MIN_VALUE, model->gvarData[index].getMax(), model->gvarData[index].getMin()); + setGVSB(gvMax[index], model->gvarData[index].getMin(), GVAR_MAX_VALUE, model->gvarData[index].getMax()); + gvPopups[index]->setChecked(model->gvarData[index].popup); + } + lock = false; +} + +void FlightModePanel::setGVSB(QDoubleSpinBox * sb, int min, int max, int val) +{ + int idx = sb->property("index").toInt(); + float mul = model->gvarData[idx].multiplierGet(); + sb->setDecimals(model->gvarData[idx].prec); + sb->setSingleStep(mul); + sb->setSuffix(model->gvarData[idx].unitToString()); + sb->setMinimum(min * mul); + sb->setMaximum(max * mul); + sb->setValue(val * mul); +} + +void FlightModePanel::populateGvarUnitCB(QComboBox * cb) +{ + cb->clear(); + cb->addItem(QObject::tr("")); + cb->addItem(QObject::tr("%")); +} + +void FlightModePanel::populateGvarPrecCB(QComboBox * cb) +{ + cb->clear(); + cb->addItem(QObject::tr("0._")); + cb->addItem(QObject::tr("0.0")); +} void FlightModePanel::phaseName_editingFinished() { @@ -341,9 +438,9 @@ void FlightModePanel::phaseGVValue_editingFinished() { if (!lock) { - QSpinBox *spinBox = qobject_cast(sender()); + QDoubleSpinBox *spinBox = qobject_cast(sender()); int gvar = spinBox->property("index").toInt(); - phase.gvars[gvar] = spinBox->value(); + phase.gvars[gvar] = spinBox->value() * model->gvarData[gvar].multiplierSet(); emit modified(); } } @@ -353,8 +450,8 @@ if (!lock) { QLineEdit *lineedit = qobject_cast(sender()); int gvar = lineedit->property("index").toInt(); - memset(&model->gvars_names[gvar], 0, sizeof(model->gvars_names[gvar])); - strcpy(model->gvars_names[gvar], lineedit->text().toLatin1()); + memset(&model->gvarData[gvar].name, 0, sizeof(model->gvarData[gvar].name)); + strcpy(model->gvarData[gvar].name, lineedit->text().toLatin1()); emit modified(); } } @@ -369,28 +466,98 @@ phase.gvars[gvar] = 0; } else { - phase.gvars[gvar] = 1024 + index; + phase.gvars[gvar] = GVAR_MAX_VALUE + index; } - update(); + updateGVar(gvar); emit modified(); lock = false; } } +void FlightModePanel::phaseGVUnit_currentIndexChanged(int index) +{ + if (!lock) { + QComboBox *comboBox = qobject_cast(sender()); + int gvar = comboBox->property("index").toInt(); + model->gvarData[gvar].unit = index; + emit modified(); + updateGVar(gvar); + } +} + +void FlightModePanel::phaseGVPrec_currentIndexChanged(int index) +{ + if (!lock) { + QComboBox *comboBox = qobject_cast(sender()); + int gvar = comboBox->property("index").toInt(); + model->gvarData[gvar].prec = index; + emit modified(); + updateGVar(gvar); + } +} + +void FlightModePanel::phaseGVMin_editingFinished() +{ + if (!lock) { + QDoubleSpinBox *spinBox = qobject_cast(sender()); + int gvar = spinBox->property("index").toInt(); + model->gvarData[gvar].setMin(spinBox->value()); + if (!model->isGVarLinked(phaseIdx, gvar)) { + if (model->getGVarFieldValuePrec(phaseIdx, gvar) < spinBox->value()) { + phase.gvars[gvar] = model->gvarData[gvar].getMin(); + } + } + for (int x=1; xgetCapability(FlightModes); x++) { + if (!model->isGVarLinked(x, gvar)) { + if (model->flightModeData[x].gvars[gvar] < model->gvarData[gvar].getMin()) { + model->flightModeData[x].gvars[gvar] = model->gvarData[gvar].getMin(); + } + } + } + emit modified(); + updateGVar(gvar); + } +} + +void FlightModePanel::phaseGVMax_editingFinished() +{ + if (!lock) { + QDoubleSpinBox *spinBox = qobject_cast(sender()); + int gvar = spinBox->property("index").toInt(); + model->gvarData[gvar].setMax(spinBox->value()); + if (!model->isGVarLinked(phaseIdx, gvar)) { + if (model->getGVarFieldValuePrec(phaseIdx, gvar) > spinBox->value()) { + phase.gvars[gvar] = model->gvarData[gvar].getMax(); + } + } + for (int x=1; xgetCapability(FlightModes); x++) { + if (!model->isGVarLinked(x, gvar)) { + if (model->flightModeData[x].gvars[gvar] > model->gvarData[gvar].getMax()) { + model->flightModeData[x].gvars[gvar] = model->gvarData[gvar].getMax(); + } + } + } + emit modified(); + updateGVar(gvar); + } +} + void FlightModePanel::phaseGVPopupToggled(bool checked) { - QCheckBox *cb = qobject_cast(sender()); - int gvar = cb->property("index").toInt(); - model->gvars_popups[gvar] = checked; - emit modified(); + if (!lock) { + QCheckBox *cb = qobject_cast(sender()); + int gvar = cb->property("index").toInt(); + model->gvarData[gvar].popup = checked; + emit modified(); + } } void FlightModePanel::phaseREValue_editingFinished() { if (!lock) { QSpinBox *spinBox = qobject_cast(sender()); - int gvar = spinBox->property("index").toInt(); - phase.rotaryEncoders[gvar] = spinBox->value(); + int re = spinBox->property("index").toInt(); + phase.rotaryEncoders[re] = spinBox->value(); emit modified(); } } @@ -474,11 +641,11 @@ void FlightModePanel::name_customContextMenuRequested(const QPoint & pos) { - QLabel *label = (QLabel *)sender(); - QPoint globalPos = label->mapToGlobal(pos); - QMenu contextMenu; - contextMenu.addAction(CompanionIcon("clear.png"), tr("&Clear"),this,SLOT(fmClear()),tr("Clear")); - contextMenu.exec(globalPos); + QLabel *label = (QLabel *)sender(); + QPoint globalPos = label->mapToGlobal(pos); + QMenu contextMenu; + contextMenu.addAction(CompanionIcon("clear.png"), tr("&Clear"),this,SLOT(fmClear()),tr("Clear")); + contextMenu.exec(globalPos); } void FlightModePanel::fmClear() @@ -489,8 +656,7 @@ if (phaseIdx == 0) { if (IS_HORUS_OR_TARANIS(getCurrentBoard())) { for (int i=0; i < gvCount; ++i) { - memset(&model->gvars_names[i], 0, sizeof(model->gvars_names[i])); - model->gvars_popups[i] = 0; + model->gvarData[i].clear(); } } } @@ -501,11 +667,11 @@ pswtch->setCurrentIndex(pswtch->findText(item.toString())); if (gvCount > 0 && (firmware->getCapability(GvarsFlightModes))) { for (int i=0; isetCurrentIndex((phase.gvars[i] > 1024 ? (phase.gvars[i] - 1024) : 0)); + gvUse[i]->setCurrentIndex((phase.gvars[i] > GVAR_MAX_VALUE ? (phase.gvars[i] - GVAR_MAX_VALUE) : 0)); } } for (int i=0; isetCurrentIndex((phase.rotaryEncoders[i] > 1024 ? (phase.rotaryEncoders[i] - 1024) : 0)); + reUse[i]->setCurrentIndex((phase.rotaryEncoders[i] > GVAR_MAX_VALUE ? (phase.rotaryEncoders[i] - GVAR_MAX_VALUE) : 0)); } lock = false; } @@ -515,6 +681,36 @@ } } +void FlightModePanel::gvLabel_customContextMenuRequested(const QPoint & pos) +{ + QLabel *label = (QLabel *)sender(); + gvIdx = label->property("index").toInt(); + QPoint globalPos = label->mapToGlobal(pos); + QMenu contextMenu; + contextMenu.addAction(CompanionIcon("clear.png"), tr("&Clear"),this,SLOT(gvClear()),tr("Clear")); + contextMenu.exec(globalPos); +} + +void FlightModePanel::gvClear() +{ + if (phaseIdx == 0) { + if (IS_HORUS_OR_TARANIS(getCurrentBoard())) { + model->gvarData[gvIdx].clear(); + phase.gvars[gvIdx] = 0; + } + } + else { + lock = true; + if (gvCount > 0 && (firmware->getCapability(GvarsFlightModes))) { + phase.gvars[gvIdx] = GVAR_MAX_VALUE + 1; + gvUse[gvIdx]->setCurrentIndex(1); + } + lock = false; + } + update(); + emit modified(); +} + /**********************************************************/ FlightModesPanel::FlightModesPanel(QWidget * parent, ModelData & model, GeneralSettings & generalSettings, Firmware * firmware): @@ -524,7 +720,7 @@ QGridLayout * gridLayout = new QGridLayout(this); tabWidget = new QTabWidget(this); for (int i=0; isetProperty("index", i); panels << tab; connect(tab, SIGNAL(modified()), this, SLOT(onPhaseModified())); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/flightmodes.h opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/flightmodes.h --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/flightmodes.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/flightmodes.h 2017-11-11 11:29:14.000000000 +0000 @@ -24,6 +24,8 @@ #include "modeledit.h" #include "eeprominterface.h" +class RawSwitchFilterItemModel; + namespace Ui { class FlightMode; } @@ -53,10 +55,16 @@ void phaseGVValue_editingFinished(); void phaseGVUse_currentIndexChanged(int index); void phaseGVPopupToggled(bool checked); + void phaseGVUnit_currentIndexChanged(int index); + void phaseGVPrec_currentIndexChanged(int index); + void phaseGVMin_editingFinished(); + void phaseGVMax_editingFinished(); void phaseREValue_editingFinished(); void phaseREUse_currentIndexChanged(int index); void name_customContextMenuRequested(const QPoint & pos); void fmClear(); + void gvLabel_customContextMenuRequested(const QPoint & pos); + void gvClear(); private: Ui::FlightMode *ui; @@ -64,19 +72,28 @@ FlightModeData & phase; int reCount; int gvCount; + int gvIdx; QVector trimsLabel; QLineEdit * gvNames[CPN_MAX_GVARS]; - QSpinBox * gvValues[CPN_MAX_GVARS]; + QDoubleSpinBox * gvValues[CPN_MAX_GVARS]; QCheckBox * gvPopups[CPN_MAX_GVARS]; QComboBox * gvUse[CPN_MAX_GVARS]; + QComboBox * gvUnit[CPN_MAX_GVARS]; + QComboBox * gvPrec[CPN_MAX_GVARS]; + QDoubleSpinBox * gvMin[CPN_MAX_GVARS]; + QDoubleSpinBox * gvMax[CPN_MAX_GVARS]; QSpinBox * reValues[CPN_MAX_ENCODERS]; QComboBox * reUse[CPN_MAX_ENCODERS]; QVector trimsUse; QVector trimsValue; QVector trimsSlider; + RawSwitchFilterItemModel * rawSwitchItemModel; void trimUpdate(unsigned int trim); - + void updateGVar(int index); + void setGVSB(QDoubleSpinBox * spinBox, int min, int max, int val); + void populateGvarUnitCB(QComboBox * cb); + void populateGvarPrecCB(QComboBox * cb); }; class FlightModesPanel : public ModelPanel diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/inputs.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/inputs.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/inputs.cpp 2017-05-14 17:18:57.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/inputs.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -75,27 +75,24 @@ // i -> mixer number QByteArray qba; ExposlistWidget->clear(); - firstLine = true; int curDest = -1; for (int i=0; iexpoData[i]; - if (md->mode==0) break; + if (!md->mode) + break; - QString str; - - while (curDest<(int)md->chn-1) { + while (curDest < (int)md->chn-1) { curDest++; AddInputLine(-curDest-1); } if (AddInputLine(i)) { curDest++; } - } - while (curDest= 0) { //add input data ExpoData *md = &model->expoData[dest]; qba.append((const char*)md, sizeof(ExpoData)); + destId = md->chn + 1; + hasSibs = (dest < CPN_MAX_EXPOS && model->expoData[dest+1].chn == md->chn); } itm->setData(Qt::UserRole, qba); -#if MIX_ROW_HEIGHT_INCREASE > 0 - if (new_ch && !firstLine) { - //increase size of this row - itm->setData(GroupHeaderRole, 1); - } -#endif - ExposlistWidget->addItem(itm); - firstLine = false; + ExposlistWidget->addItem(itm, destId, new_ch, hasSibs); //qDebug() << "InputsPanel::AddInputLine(): dest" << dest << "text" << str; return new_ch; } @@ -300,13 +294,17 @@ void InputsPanel::mimeExpoDropped(int index, const QMimeData *data, Qt::DropAction action) { - int idx = ExposlistWidget->item(index > 0 ? index-1 : 0)->data(Qt::UserRole).toByteArray().at(0); + int idx = ExposlistWidget->item(index)->data(Qt::UserRole).toByteArray().at(0); if (action==Qt::CopyAction) { pasteExpoMimeData(data, idx); } else if (action==Qt::MoveAction) { QList list = createExpoListFromSelected(); exposDeleteList(list); + foreach (const int del, list) { + if (del < idx) + --idx; + } pasteExpoMimeData(data, idx); } } @@ -391,6 +389,7 @@ if (!gm_insertExpo(index)) return; model->expoData[index].chn = model->expoData[index-1].chn; + expoInserted=true; } gm_openExpo(index); } @@ -416,6 +415,8 @@ contextMenu.addSeparator(); contextMenu.addAction(CompanionIcon("moveup.png"), tr("Move Up"),this,SLOT(moveExpoUp()),tr("Ctrl+Up")); contextMenu.addAction(CompanionIcon("movedown.png"), tr("Move Down"),this,SLOT(moveExpoDown()),tr("Ctrl+Down")); + contextMenu.addSeparator(); + contextMenu.addActions(ExposlistWidget->actions()); contextMenu.exec(globalPos); } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/inputs.h opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/inputs.h --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/inputs.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/inputs.h 2017-10-31 16:16:43.000000000 +0000 @@ -54,7 +54,6 @@ private: bool expoInserted; MixersListWidget *ExposlistWidget; - bool firstLine; int inputsCount; ModelPrinter modelPrinter; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/logicalswitches.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/logicalswitches.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/logicalswitches.cpp 2017-05-31 19:49:19.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/logicalswitches.cpp 2017-11-15 20:54:40.000000000 +0000 @@ -19,6 +19,7 @@ */ #include "logicalswitches.h" +#include "switchitemmodel.h" #include "helpers.h" LogicalSwitchesPanel::LogicalSwitchesPanel(QWidget * parent, ModelData & model, GeneralSettings & generalSettings, Firmware * firmware): @@ -28,8 +29,7 @@ Stopwatch s1("LogicalSwitchesPanel"); int channelsMax = model.getChannelsMax(true); - rawSwitchItemModel = Helpers::getRawSwitchItemModel(&generalSettings, Helpers::LogicalSwitchesContext); - rawSwitchItemModel->setParent(this); + rawSwitchItemModel = new RawSwitchFilterItemModel(&generalSettings, &model, LogicalSwitchesContext); int srcFlags = POPULATE_NONE | POPULATE_SOURCES | POPULATE_SCRIPT_OUTPUTS | POPULATE_VIRTUAL_INPUTS | POPULATE_TRIMS | POPULATE_SWITCHES | POPULATE_TELEMETRY | (firmware->getCapability(GvarsInCS) ? POPULATE_GVARS : 0); rawSourceItemModel = Helpers::getRawSourceItemModel(&generalSettings, &model, srcFlags); rawSourceItemModel->setParent(this); @@ -510,6 +510,7 @@ LogicalSwitchData *csw = &model->logicalSw[selectedSwitch]; memcpy(csw, cswData.constData(), sizeof(LogicalSwitchData)); emit modified(); + rawSwitchItemModel->update(); updateLine(selectedSwitch); } } @@ -549,10 +550,10 @@ bool hasData = mimeData->hasFormat("application/x-companion-csw"); QMenu contextMenu; - contextMenu.addAction(CompanionIcon("copy.png"), tr("&Copy"),this,SLOT(cswCopy()),tr("Ctrl+C")); - contextMenu.addAction(CompanionIcon("cut.png"), tr("&Cut"),this,SLOT(cswCut()),tr("Ctrl+X")); - contextMenu.addAction(CompanionIcon("paste.png"), tr("&Paste"),this,SLOT(cswPaste()),tr("Ctrl+V"))->setEnabled(hasData); - contextMenu.addAction(CompanionIcon("clear.png"), tr("&Delete"),this,SLOT(cswDelete()),tr("Delete")); + contextMenu.addAction(CompanionIcon("copy.png"), tr("&Copy"),this,SLOT(cswCopy())); + contextMenu.addAction(CompanionIcon("cut.png"), tr("&Cut"),this,SLOT(cswCut())); + contextMenu.addAction(CompanionIcon("paste.png"), tr("&Paste"),this,SLOT(cswPaste()))->setEnabled(hasData); + contextMenu.addAction(CompanionIcon("clear.png"), tr("&Delete"),this,SLOT(cswDelete())); contextMenu.exec(globalPos); } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/logicalswitches.h opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/logicalswitches.h --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/logicalswitches.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/logicalswitches.h 2017-10-31 16:16:43.000000000 +0000 @@ -22,7 +22,9 @@ #define _LOGICALSWITCHES_H_ #include "modeledit.h" -#include "eeprominterface.h" +#include "radiodata.h" + +class RawSwitchFilterItemModel; class LogicalSwitchesPanel : public ModelPanel { @@ -58,7 +60,7 @@ QDoubleSpinBox * cswitchDelay[CPN_MAX_LOGICAL_SWITCHES]; QComboBox * cswitchSource1[CPN_MAX_LOGICAL_SWITCHES]; QComboBox * cswitchSource2[CPN_MAX_LOGICAL_SWITCHES]; - QStandardItemModel * rawSwitchItemModel; + RawSwitchFilterItemModel * rawSwitchItemModel; QStandardItemModel * rawSourceItemModel; void setSwitchWidgetVisibility(int i); int selectedSwitch; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/mixerdialog.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/mixerdialog.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/mixerdialog.cpp 2017-05-14 17:18:57.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/mixerdialog.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -20,10 +20,11 @@ #include "mixerdialog.h" #include "ui_mixerdialog.h" -#include "eeprominterface.h" +#include "radiodata.h" +#include "switchitemmodel.h" #include "helpers.h" -MixerDialog::MixerDialog(QWidget *parent, ModelData & model, MixData *mixdata, GeneralSettings & generalSettings, Firmware * firmware) : +MixerDialog::MixerDialog(QWidget *parent, ModelData & model, MixData * mixdata, GeneralSettings & generalSettings, Firmware * firmware) : QDialog(parent), ui(new Ui::MixerDialog), model(model), @@ -103,7 +104,7 @@ } } - ui->switchesCB->setModel(Helpers::getRawSwitchItemModel(&generalSettings, Helpers::MixesContext)); + ui->switchesCB->setModel(new RawSwitchFilterItemModel(&generalSettings, &model, MixesContext)); ui->switchesCB->setCurrentIndex(ui->switchesCB->findData(md->swtch.toValue())); ui->warningCB->setCurrentIndex(md->mixWarn); ui->mltpxCB->setCurrentIndex(md->mltpx); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/mixerslistwidget.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/mixerslistwidget.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/mixerslistwidget.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/mixerslistwidget.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -20,140 +20,256 @@ #include "mixerslistwidget.h" +#define GRP_IS_PARENT 0x01 +#define GRP_HAS_SIBLING 0x02 +#define GRP_HAS_DATA 0x04 + +#define GroupIdRole (Qt::UserRole+1) // destination Input/Channel, for alternate row colors +#define GroupHeaderRole (Qt::UserRole+2) // bitfield of row metadata (see addItem()) + +static QFont defaultFont; +static bool fontInit = false; + MixersListWidget::MixersListWidget(QWidget * parent, bool expo) : - QListWidget(parent), - expo(expo) + QListWidget(parent), + expo(expo) { - setFont(QFont("Courier New",12)); - setContextMenuPolicy(Qt::CustomContextMenu); - setSelectionMode(QAbstractItemView::SingleSelection); - setDragEnabled(true); - setAcceptDrops(true); - setDropIndicatorShown(true); - setItemDelegate(new MixersDelegate(parent)); //set custom paint handler + if (!fontInit) { + fontInit = true; + defaultFont = font(); + defaultFont.setFamily("Courier"); + defaultFont.setStyleHint(QFont::TypeWriter); + defaultFont.setPointSize(defaultFont.pointSize() + 3); + } + + setFont(defaultFont); + setContextMenuPolicy(Qt::CustomContextMenu); + setSelectionMode(QAbstractItemView::SingleSelection); + setSelectionBehavior(QAbstractItemView::SelectRows); + setDragEnabled(true); + setAcceptDrops(true); + setDragDropMode(QAbstractItemView::DragDrop); + setDropIndicatorShown(true); + setItemDelegate(new MixersDelegate(this)); // set custom paint handler + setStyle(new MixerItemViewProxyStyle(style())); // custom element style painter + + itemMimeFmt = (expo ? "application/x-companion-expo-item" : "application/x-companion-mix-item"); + + QAction * zin = new QAction(tr("Increase font size"), this); + zin->setShortcut(QKeySequence::ZoomIn); + zin->setData(1); + addAction(zin); + QAction * zout = new QAction(tr("Decrease font size"), this); + zout->setShortcut(QKeySequence::ZoomOut); + zout->setData(-1); + addAction(zout); + QAction * zrst = new QAction(tr("Default font size"), this); + zrst->setShortcut(tr("Ctrl+0")); + zrst->setData(0); + addAction(zrst); + connect(zin, &QAction::triggered, this, &MixersListWidget::zoomView); + connect(zout, &QAction::triggered, this, &MixersListWidget::zoomView); + connect(zrst, &QAction::triggered, this, &MixersListWidget::zoomView); } void MixersListWidget::keyPressEvent(QKeyEvent *event) { - emit keyWasPressed(event); + emit keyWasPressed(event); } +void MixersListWidget::addItem(QListWidgetItem * item, const unsigned & rowId, bool topLevel, bool hasSib) +{ + Qt::ItemFlags f = item->flags(); + f |= Qt::ItemIsDropEnabled; + + quint8 hdrRole = 0; + if (topLevel) + hdrRole |= GRP_IS_PARENT; + if (hasSib) + hdrRole |= GRP_HAS_SIBLING; + if (item->data(Qt::UserRole).toByteArray().at(0) > -1) + hdrRole |= GRP_HAS_DATA; + else + f &= ~Qt::ItemIsDragEnabled; // prevent drag of empty items + + item->setData(GroupIdRole, rowId); + item->setData(GroupHeaderRole, hdrRole); + item->setFlags(f); + + QListWidget::addItem(item); + //qDebug() << rowId << topLevel << hasSib << item->data(GroupHeaderRole).toUInt(); +} /** @brief Override to give us different mime type for mixers and inputs */ QStringList MixersListWidget::mimeTypes () const { - QStringList types; - if (expo) types << "application/x-companion-expo-item"; - else types << "application/x-companion-mix-item"; - return types; + return QStringList() << itemMimeFmt; } void MixersListWidget::dropEvent(QDropEvent * event) { - QList list; - foreach(QListWidgetItem *item, selectedItems()) { - int idx= item->data(Qt::UserRole).toByteArray().at(0); - if(idx >= 0) list << idx; + if (event->proposedAction() == Qt::IgnoreAction) + return; + + if (event->mimeData() && event->mimeData()->hasFormat(itemMimeFmt)) { + if (event->source() != this) { + // force a copy action if dragging from another window + event->setDropAction(Qt::CopyAction); + event->accept(); } - if (list.count()<1) return; - event->acceptProposedAction(); - dropMimeData(indexAt(event->pos()).row(),event->mimeData(),event->dropAction()); + else { + event->acceptProposedAction(); + } + dropMimeData(indexAt(event->pos()).row(), event->mimeData(), event->dropAction()); + } } bool MixersListWidget::dropMimeData(int index, const QMimeData * data, Qt::DropAction action ) { - // qDebug() << "MixersListWidget::dropMimeData() index:" << index << "formats" << data->formats(); - QByteArray dropData = data->data(expo ? "application/x-companion-expo-item" : "application/x-companion-mix-item"); - if (dropData.isNull() ) return false; - QDataStream stream(&dropData, QIODevice::ReadOnly); - QByteArray qba; - - while (!stream.atEnd()) { - int r,c; - QMap v; - stream >> r >> c >> v; - QList lsVars; - lsVars = v.values(); - qba.append(lsVars.at(1).toByteArray().mid(1)); - // qDebug() << "MixersListWidget::dropMimeData() added" << lsVars.count() << "items, data:" << lsVars; - } + // qDebug() << "index:" << index << action << "formats" << data->formats(); + QByteArray dropData = data->data(itemMimeFmt); + if (dropData.isEmpty() ) + return false; + + QDataStream stream(&dropData, QIODevice::ReadOnly); + QByteArray qba; + + while (!stream.atEnd()) { + int r,c; + QMap v; + stream >> r >> c >> v; + qba.append(v.values().at(1).toByteArray().mid(1)); + } + + if(qba.size()) { + QMimeData mimeData; + mimeData.setData(QString(itemMimeFmt).remove("-item"), qba); + emit mimeDropped(index, &mimeData, action); + } - if(qba.length()>0) { - QMimeData *mimeData = new QMimeData; - mimeData->setData(expo ? "application/x-companion-expo" : "application/x-companion-mix", qba); - emit mimeDropped(index, mimeData, action); - delete mimeData; //is this correct? is mimeData freed elswere?? - } + return true; +} - return true; +void MixersListWidget::zoomView() +{ + static int origSz = QFontInfo(font()).pixelSize(); + int fsz = origSz; + int step = qobject_cast(sender())->data().toInt(); + if (step) + fsz = QFontInfo(font()).pixelSize() + step; + if (fsz < 8) + return; + + QFont fnt(font()); + fnt.setPixelSize(fsz); + setFont(fnt); + defaultFont = fnt; } + +/* + * MixersDelegate +*/ + /** @brief Paints our HTML formated list item text */ void MixersDelegate::paint(QPainter *painter, const QStyleOptionViewItem &option, const QModelIndex &index) const { - QStyleOptionViewItem options = option; - initStyleOption(&options, index); + QStyleOptionViewItem options = option; + initStyleOption(&options, index); - painter->save(); - - //setup html document - QTextDocument doc; - SetupDocument(doc, options); - - options.text = ""; - options.widget->style()->drawControl(QStyle::CE_ItemViewItem, &options, painter); - - if ( index.model()->data(index, GroupHeaderRole).toInt() > 0 ) { - //paint with added space - painter->translate(options.rect.left(), options.rect.top() + MIX_ROW_HEIGHT_INCREASE); - QRect clip(0, 0, options.rect.width(), options.rect.height() - MIX_ROW_HEIGHT_INCREASE); - doc.drawContents(painter, clip); - } - else { - painter->translate(options.rect.left(), options.rect.top()); - QRect clip(0, 0, options.rect.width(), options.rect.height()); - doc.drawContents(painter, clip); - } - painter->restore(); + QTextDocument doc; + SetupDocument(doc, options, index); + options.text.clear(); + + QAbstractTextDocumentLayout::PaintContext ctx; + if (options.widget) + ctx.palette = options.widget->palette(); + + QBrush brush = ((index.data(GroupIdRole).toUInt() % 2) ? ctx.palette.base() : ctx.palette.alternateBase()); + options.backgroundBrush = brush; + + if (!(index.model()->data(index, GroupHeaderRole).toUInt() & GRP_HAS_DATA)) { + // lighter text for empty lines + ctx.palette.setBrush(QPalette::Text, ctx.palette.mid()); + } +#ifndef Q_OS_WIN + // Linux and OS X show a solid dark blue color on selected items + else if ((options.state & QStyle::State_Selected)) { + ctx.palette.setBrush(QPalette::Text, ctx.palette.highlightedText()); + } +#endif + + QStyle * style = (options.widget ? options.widget->style() : QApplication::style()); + style->drawControl(QStyle::CE_ItemViewItem, &options, painter, options.widget); + + QRect textRect = style->subElementRect(QStyle::SE_ItemViewItemText, &options); + QRectF clipRect = textRect.translated(-textRect.topLeft()); + ctx.clip = clipRect; + painter->save(); + painter->translate(textRect.topLeft()); + painter->setClipRect(clipRect); + doc.documentLayout()->draw(painter, ctx); + painter->restore(); } /** @brief Returns needed size for our HTML formated list item text */ -QSize MixersDelegate::sizeHint ( const QStyleOptionViewItem & option, const QModelIndex & index ) const +QSize MixersDelegate::sizeHint (const QStyleOptionViewItem & option, const QModelIndex & index) const { - QStyleOptionViewItem options = option; - initStyleOption(&options, index); + QStyleOptionViewItem options = option; + initStyleOption(&options, index); - //setup html document - QTextDocument doc; - SetupDocument(doc, options); - - //qDebug() << "MixersDelegate::sizeHint() UserRole-> " << index.model()->data(index, Qt::UserRole + 2); - int height = doc.size().height(); - if ( index.model()->data(index, Qt::UserRole + 2).toInt() > 0 ) { - //qDebug() << "MixersDelegate::sizeHint() detected channel head"; - height = doc.size().height() + MIX_ROW_HEIGHT_INCREASE; - } - //qDebug() << "MixersDelegate::sizeHint() options.rect " << options.rect; - //qDebug() << "MixersDelegate::sizeHint() result " << QSize(doc.idealWidth(), height) << options.rect.width(); - return QSize(doc.idealWidth(), height); -} - -void MixersDelegate::SetupDocument(QTextDocument & doc, const QStyleOptionViewItem & options) const -{ - //setup html document - doc.setHtml(options.text); - doc.setDefaultFont(options.font); - - //minimize margins (default margins look ugly) - QTextFrame *tf = doc.rootFrame(); - QTextFrameFormat tff = tf->frameFormat(); - tff.setMargin(0); - tf->setFrameFormat(tff); + QTextDocument doc; + SetupDocument(doc, options, index); + return QSize(doc.idealWidth(), doc.size().height()); +} + +void MixersDelegate::SetupDocument(QTextDocument & doc, const QStyleOptionViewItem & options, const QModelIndex & index) const +{ + //setup html document + quint8 hdrRole = index.model()->data(index, GroupHeaderRole).toUInt(); + + doc.setDefaultFont(options.font); + doc.setHtml(options.text); + + // adjust margins to visually group items per input/channel + QTextFrame *tf = doc.rootFrame(); + QTextFrameFormat tff = tf->frameFormat(); + + if (!(hdrRole & GRP_HAS_DATA)) { + tff.setTopMargin(0.75f); + tff.setBottomMargin(0.75f); + } + else { + if (!(hdrRole & GRP_IS_PARENT)) + tff.setTopMargin(0.5f); + if (hdrRole & GRP_HAS_SIBLING) + tff.setBottomMargin(0.5f); + } + tf->setFrameFormat(tff); +} + + +/* + * MixerItemViewProxyStyle +*/ + +void MixerItemViewProxyStyle::drawPrimitive(QStyle::PrimitiveElement element, const QStyleOption * option, QPainter * painter, const QWidget * widget) const +{ + painter->save(); + if (element == QStyle::PE_IndicatorItemViewItemDrop) { + painter->setRenderHint(QPainter::HighQualityAntialiasing, true); + // set a wider stroke for the drop indicator + QPen pen(painter->pen()); + pen.setWidthF(2.25f); + painter->setPen(pen); + } + QProxyStyle::drawPrimitive(element, option, painter, widget); + painter->restore(); } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/mixerslistwidget.h opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/mixerslistwidget.h --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/mixerslistwidget.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/mixerslistwidget.h 2017-10-31 16:16:43.000000000 +0000 @@ -22,9 +22,9 @@ #define _MIXERSLISTWIDGET_H_ #include - -#define MIX_ROW_HEIGHT_INCREASE 8 //how much space is added above mixer row (for new channel), if 0 space adding is disabled -const int GroupHeaderRole = (Qt::UserRole+2); //defines new user role for list items. If value is > 0, then space is added before that item +#include +#include +#include class MixersListWidget : public QListWidget { @@ -40,13 +40,15 @@ void keyWasPressed(QKeyEvent *event); public slots: + void addItem(QListWidgetItem *item, const unsigned & rowId, bool topLevel = false, bool hasSib = false); bool dropMimeData(int index, const QMimeData *data, Qt::DropAction action); + void zoomView(); protected: virtual QStringList mimeTypes() const; private: - QPoint dragStartPosition; + QString itemMimeFmt; bool expo; }; @@ -60,14 +62,25 @@ { Q_OBJECT public: - inline MixersDelegate(QObject *parent) : QStyledItemDelegate(parent) {}; + inline MixersDelegate(QObject *parent) : QStyledItemDelegate(parent) {} void paint(QPainter *painter, const QStyleOptionViewItem &option, const QModelIndex &index) const; QSize sizeHint ( const QStyleOptionViewItem & option, const QModelIndex & index ) const; private: - void SetupDocument(QTextDocument & doc, const QStyleOptionViewItem & options) const; + void SetupDocument(QTextDocument & doc, const QStyleOptionViewItem & options, const QModelIndex & index) const; + +}; + +/** + @brief Provides custom painting of items on a per-element basis, eg. to change style of drop indicator +*/ +class MixerItemViewProxyStyle: public QProxyStyle +{ + public: + explicit MixerItemViewProxyStyle(QStyle * style = 0) : QProxyStyle(style) {} + void drawPrimitive(PrimitiveElement element, const QStyleOption * option, QPainter * painter, const QWidget * widget = 0) const; }; #endif // _MIXERSLISTWIDGET_H_ diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/mixes.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/mixes.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/mixes.cpp 2017-04-29 16:57:04.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/mixes.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -109,20 +109,17 @@ QString str = getMixerText(dest, &new_ch); QListWidgetItem *itm = new QListWidgetItem(str); QByteArray qba(1, (quint8)dest); + unsigned destId = abs(dest); + bool hasSibs = false; if (dest >= 0) { //add mix data MixData * md = &model->mixData[dest]; qba.append((const char*)md, sizeof(MixData)); + destId = md->destCh; + hasSibs = (dest < CPN_MAX_MIXERS && model->mixData[dest+1].destCh == md->destCh); } itm->setData(Qt::UserRole, qba); -#if MIX_ROW_HEIGHT_INCREASE > 0 - // TODO why? - if (new_ch && mixersListWidget->count() == 0) { - // increase size of this row - itm->setData(GroupHeaderRole, 1); - } -#endif - mixersListWidget->addItem(itm); + mixersListWidget->addItem(itm, destId, new_ch, hasSibs); return new_ch; } @@ -140,11 +137,11 @@ QString str; bool newChannel = false; if (dest < 0) { - str = modelPrinter.printChannelName(abs(dest)-1); + dest = abs(dest); + str = modelPrinter.printChannelName(dest-1); //highlight channel if needed - if (-dest == (int)highlightedSource) { + if (dest == (int)highlightedSource) str = "" + str + ""; - } newChannel = true; } else { @@ -155,9 +152,8 @@ if ((dest == 0) || (model->mixData[dest-1].destCh != mix.destCh)) { newChannel = true; //highlight channel if needed - if (mix.destCh == highlightedSource) { + if (mix.destCh == highlightedSource) str = "" + str + ""; - } } else { str.fill(' '); @@ -165,7 +161,8 @@ str += modelPrinter.printMixerLine(mix, !newChannel, highlightedSource); } - if (new_ch) *new_ch = newChannel; + if (new_ch) + *new_ch = newChannel; return str.replace(" ", " "); } @@ -446,21 +443,27 @@ contextMenu.addSeparator(); contextMenu.addAction(CompanionIcon("moveup.png"), tr("Move Up"), this, SLOT(moveMixUp()), tr("Ctrl+Up")); contextMenu.addAction(CompanionIcon("movedown.png"), tr("Move Down"), this, SLOT(moveMixDown()), tr("Ctrl+Down")); + contextMenu.addSeparator(); + contextMenu.addActions(mixersListWidget->actions()); contextMenu.exec(globalPos); } void MixesPanel::mimeMixerDropped(int index, const QMimeData *data, Qt::DropAction action) { - int idx= mixersListWidget->item(index > 0 ? index-1 : 0)->data(Qt::UserRole).toByteArray().at(0); + int idx = mixersListWidget->item(index)->data(Qt::UserRole).toByteArray().at(0); //qDebug() << "MixesPanel::mimeMixerDropped()" << index << data; - if (action==Qt::CopyAction) { - pasteMixerMimeData(data, idx); + if (action == Qt::CopyAction) { + pasteMixerMimeData(data, idx); } - else if (action==Qt::MoveAction) { - QList list = createMixListFromSelected(); - mixersDeleteList(list); - pasteMixerMimeData(data, idx); + else if (action == Qt::MoveAction) { + QList list = createMixListFromSelected(); + mixersDeleteList(createMixListFromSelected()); + foreach (const int del, list) { + if (del < idx) + --idx; + } + pasteMixerMimeData(data, idx); } } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/setup.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/setup.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/setup.cpp 2017-05-14 17:18:57.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/setup.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -22,10 +22,12 @@ #include "ui_setup.h" #include "ui_setup_timer.h" #include "ui_setup_module.h" +#include "switchitemmodel.h" #include "helpers.h" #include "appdata.h" #include "modelprinter.h" #include "multiprotocols.h" +#include "checklistdialog.h" TimerPanel::TimerPanel(QWidget *parent, ModelData & model, TimerData & timer, GeneralSettings & generalSettings, Firmware * firmware, QWidget * prevFocus): ModelPanel(parent, model, generalSettings, firmware), @@ -49,7 +51,8 @@ } // Mode - ui->mode->setModel(Helpers::getRawSwitchItemModel(&generalSettings, Helpers::TimersContext)); + rawSwitchItemModel = new RawSwitchFilterItemModel(&generalSettings, &model, TimersContext); + ui->mode->setModel(rawSwitchItemModel); ui->mode->setCurrentIndex(ui->mode->findData(timer.mode.toValue())); if (!firmware->getCapability(PermTimers)) { @@ -90,6 +93,8 @@ void TimerPanel::update() { + rawSwitchItemModel->update(); + int hour = timer.val / 3600; int min = (timer.val - (hour * 3600)) / 60; int sec = (timer.val - (hour * 3600)) % 60; @@ -165,6 +170,9 @@ #define MASK_MULTIMODULE 128 #define MASK_ANTENNA 256 #define MASK_MULTIOPTION 512 +#define MASK_R9M 1024 +#define MASK_SBUSPPM_FIELDS 2048 +#define MASK_SUBTYPES 4096 quint8 ModulePanel::failsafesValueDisplayType = ModulePanel::FAILSAFE_DISPLAY_PERCENT; @@ -256,7 +264,8 @@ bool ModulePanel::moduleHasFailsafes() { - return ((PulsesProtocol)module.protocol == PulsesProtocol::PULSES_PXX_XJT_X16 && firmware->getCapability(HasFailsafe));; + return (((PulsesProtocol)module.protocol == PulsesProtocol::PULSES_PXX_XJT_X16 || (PulsesProtocol)module.protocol == PulsesProtocol::PULSES_PXX_R9M) + && firmware->getCapability(HasFailsafe));; } void ModulePanel::setupFailsafes() @@ -360,12 +369,14 @@ if (moduleIdx >= 0) { mask |= MASK_PROTOCOL; switch (protocol) { + case PULSES_PXX_R9M: + mask |= MASK_R9M | MASK_SUBTYPES; case PULSES_PXX_XJT_X16: case PULSES_PXX_XJT_D8: case PULSES_PXX_XJT_LR12: case PULSES_PXX_DJT: mask |= MASK_CHANNELS_RANGE | MASK_CHANNELS_COUNT; - if (protocol==PULSES_PXX_XJT_X16 || protocol==PULSES_PXX_XJT_LR12) + if (protocol==PULSES_PXX_XJT_X16 || protocol==PULSES_PXX_XJT_LR12 || protocol==PULSES_PXX_R9M) mask |= MASK_RX_NUMBER; if (IS_HORUS(firmware->getBoard()) && moduleIdx==0) mask |= MASK_ANTENNA; @@ -382,13 +393,17 @@ module.channelsCount = 16; break; case PULSES_PPM: - mask |= MASK_PPM_FIELDS | MASK_CHANNELS_RANGE| MASK_CHANNELS_COUNT; + mask |= MASK_PPM_FIELDS | MASK_SBUSPPM_FIELDS| MASK_CHANNELS_RANGE| MASK_CHANNELS_COUNT; if (IS_9XRPRO(firmware->getBoard())) { mask |= MASK_OPEN_DRAIN; } break; + case PULSES_SBUS: + module.channelsCount = 16; + mask |= MASK_SBUSPPM_FIELDS| MASK_CHANNELS_RANGE; + break; case PULSES_MULTIMODULE: - mask |= MASK_CHANNELS_RANGE | MASK_RX_NUMBER | MASK_MULTIMODULE; + mask |= MASK_CHANNELS_RANGE | MASK_RX_NUMBER | MASK_MULTIMODULE | MASK_SUBTYPES; max_rx_num = 15; if (module.multi.rfProtocol == MM_RF_PROTO_DSM2) mask |= MASK_CHANNELS_COUNT; @@ -396,6 +411,8 @@ module.channelsCount = 16; if (multiProtocols.getProtocol(module.multi.rfProtocol).optionsstr != nullptr) mask |= MASK_MULTIOPTION; + if (multiProtocols.getProtocol(module.multi.rfProtocol).hasFailsafe) + mask |= MASK_FAILSAFES; break; case PULSES_OFF: break; @@ -432,8 +449,8 @@ ui->channelsCount->setSingleStep(firmware->getCapability(HasPPMStart) ? 1 : 2); // PPM settings fields - ui->label_ppmPolarity->setVisible(mask & MASK_PPM_FIELDS); - ui->ppmPolarity->setVisible(mask & MASK_PPM_FIELDS); + ui->label_ppmPolarity->setVisible(mask & MASK_SBUSPPM_FIELDS); + ui->ppmPolarity->setVisible(mask & MASK_SBUSPPM_FIELDS); ui->ppmPolarity->setCurrentIndex(module.ppm.pulsePol); ui->label_ppmOutputType->setVisible(mask & MASK_OPEN_DRAIN); ui->ppmOutputType->setVisible(mask & MASK_OPEN_DRAIN); @@ -441,8 +458,8 @@ ui->label_ppmDelay->setVisible(mask & MASK_PPM_FIELDS); ui->ppmDelay->setVisible(mask & MASK_PPM_FIELDS); ui->ppmDelay->setValue(module.ppm.delay); - ui->label_ppmFrameLength->setVisible(mask & MASK_PPM_FIELDS); - ui->ppmFrameLength->setVisible(mask & MASK_PPM_FIELDS); + ui->label_ppmFrameLength->setVisible(mask & MASK_SBUSPPM_FIELDS); + ui->ppmFrameLength->setVisible(mask & MASK_SBUSPPM_FIELDS); ui->ppmFrameLength->setMinimum(module.channelsCount*(model->extendedLimits ? 2.250 : 2)+3.5); ui->ppmFrameLength->setMaximum(firmware->getCapability(PPMFrameLength)); ui->ppmFrameLength->setValue(22.5+((double)module.ppm.frameLength)*0.5); @@ -450,29 +467,51 @@ // Antenna slection on Horus ui->label_antenna->setVisible(mask & MASK_ANTENNA); ui->antennaMode->setVisible(mask & MASK_ANTENNA); - ui->antennaMode->setCurrentIndex(module.ppm.pulsePol); + ui->antennaMode->setCurrentIndex(module.pxx.external_antenna); + + // R9M options + ui->sportOut->setVisible(mask & MASK_R9M); + ui->r9mPower->setVisible((mask & MASK_R9M) && module.subType == 0); + ui->label_r9mPower->setVisible((mask & MASK_R9M) && module.subType == 0); + if (mask & MASK_R9M) { + if (model->moduleData[0].protocol >= PULSES_PXX_XJT_X16 && model->moduleData[0].protocol <= PULSES_PXX_XJT_LR12) { + module.pxx.sport_out = false; + ui->sportOut->setDisabled(true); + } + else { + ui->sportOut->setEnabled(true); + } + ui->sportOut->setChecked(module.pxx.sport_out); + ui->r9mPower->setCurrentIndex(module.pxx.power); + } + + // module subtype + ui->label_multiSubType->setVisible(mask & MASK_SUBTYPES); + ui->multiSubType->setVisible(mask & MASK_SUBTYPES); + if (mask & MASK_SUBTYPES) { + unsigned numEntries = 2; // R9M FCC/EU + if (mask & MASK_MULTIMODULE) + numEntries = (module.multi.customProto ? 8 : multiProtocols.getProtocol(module.multi.rfProtocol).numSubytes()); + + const QSignalBlocker blocker(ui->multiSubType); + ui->multiSubType->clear(); + for (unsigned i=0; i < numEntries; i++) + ui->multiSubType->addItem(ModelPrinter::printModuleSubType(protocol, i, module.multi.rfProtocol, module.multi.customProto), i); + ui->multiSubType->setCurrentIndex(module.subType); + } // Multi settings fields ui->label_multiProtocol->setVisible(mask & MASK_MULTIMODULE); ui->multiProtocol->setVisible(mask & MASK_MULTIMODULE); - ui->multiProtocol->setCurrentIndex(module.multi.rfProtocol); - ui->label_multiSubType->setVisible(mask & MASK_MULTIMODULE); - ui->multiSubType->setVisible(mask & MASK_MULTIMODULE); ui->label_option->setVisible(mask & MASK_MULTIOPTION); ui->optionValue->setVisible(mask & MASK_MULTIOPTION); + ui->autoBind->setVisible(mask & MASK_MULTIMODULE); + ui->lowPower->setVisible(mask & MASK_MULTIMODULE); if (mask & MASK_MULTIMODULE) { - int numEntries = multiProtocols.getProtocol(module.multi.rfProtocol).numSubytes(); - if (module.multi.customProto) - numEntries=8; - // Removes extra items - ui->multiSubType->setMaxCount(numEntries); - for (int i=0; i < numEntries; i++) { - if (i < ui->multiSubType->count()) - ui->multiSubType->setItemText(i, ModelPrinter::printMultiSubType(module.multi.rfProtocol, module.multi.customProto, i)); - else - ui->multiSubType->addItem(ModelPrinter::printMultiSubType(module.multi.rfProtocol, module.multi.customProto, i), (QVariant) i); - } + ui->multiProtocol->setCurrentIndex(module.multi.rfProtocol); + ui->autoBind->setChecked(module.multi.autoBindMode ? Qt::Checked : Qt::Unchecked); + ui->lowPower->setChecked(module.multi.lowPowerMode ? Qt::Checked : Qt::Unchecked); } if (mask & MASK_MULTIOPTION) { @@ -482,14 +521,8 @@ ui->optionValue->setValue(module.multi.optionValue); ui->label_option->setText(qApp->translate("Multiprotocols", qPrintable(pdef.optionsstr))); } - ui->multiSubType->setCurrentIndex(module.subType); - - ui->autoBind->setVisible(mask & MASK_MULTIMODULE); - ui->autoBind->setChecked(module.multi.autoBindMode ? Qt::Checked : Qt::Unchecked); - ui->lowPower->setVisible(mask & MASK_MULTIMODULE); - ui->lowPower->setChecked(module.multi.lowPowerMode ? Qt::Checked : Qt::Unchecked); - + // Failsafes ui->label_failsafeMode->setVisible(mask & MASK_FAILSAFES); ui->failsafeMode->setVisible(mask & MASK_FAILSAFES); @@ -554,7 +587,21 @@ void ModulePanel::on_antennaMode_currentIndexChanged(int index) { - module.ppm.pulsePol = index; + module.pxx.external_antenna = index; + emit modified(); +} + +void ModulePanel::on_sportOut_toggled(bool checked) +{ + if (module.pxx.sport_out != checked) { + module.pxx.sport_out = checked; + emit modified(); + } +} + +void ModulePanel::on_r9mPower_currentIndexChanged(int index) +{ + module.pxx.power = index; emit modified(); } @@ -891,6 +938,7 @@ if (!firmware->getCapability(HasDisplayText)) { ui->displayText->hide(); + ui->editText->hide(); } if (!firmware->getCapability(GlobalFunctions)) { @@ -1306,3 +1354,9 @@ emit modified(); } } + +void SetupPanel::on_editText_clicked() +{ + ChecklistDialog *g = new ChecklistDialog(this, ui->name->text()); + g->exec(); +} diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/setup.h opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/setup.h --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/setup.h 2017-05-14 17:18:57.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/setup.h 2017-12-17 16:22:27.000000000 +0000 @@ -24,6 +24,8 @@ #include "modeledit.h" #include "eeprominterface.h" +class RawSwitchFilterItemModel; + namespace Ui { class Setup; class Timer; @@ -49,7 +51,8 @@ private: TimerData & timer; - Ui::Timer *ui; + Ui::Timer * ui; + RawSwitchFilterItemModel * rawSwitchItemModel; }; class ModulePanel : public ModelPanel @@ -85,6 +88,8 @@ void on_multiSubType_currentIndexChanged(int index); void on_autoBind_stateChanged(int state); void on_lowPower_stateChanged(int state); + void on_sportOut_toggled(bool checked); + void on_r9mPower_currentIndexChanged(int index); void setChannelFailsafeValue(const int channel, const int value, quint8 updtSb = 0); void onFailsafeComboIndexChanged(int index); void onFailsafeUsecChanged(int value); @@ -140,6 +145,7 @@ void startupSwitchToggled(bool checked); void potWarningToggled(bool checked); void on_potWarningMode_currentIndexChanged(int index); + void on_editText_clicked(); private: Ui::Setup *ui; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/setup_module.ui opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/setup_module.ui --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/setup_module.ui 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/setup_module.ui 2017-12-17 16:22:27.000000000 +0000 @@ -6,13 +6,16 @@ 0 0 - 674 - 229 + 708 + 259 + + + 6 @@ -147,22 +150,43 @@ - + + + + 16777215 + 16777215 + + - SubType + Receiver No. + + + Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter - + 0 0 - - QComboBox::AdjustToContents + + + + + 0 + + + 63 + + + 1 + + + 0 @@ -206,87 +230,53 @@ - - - - 16777215 - 16777215 - - + - Antenna - - - Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter + RF Output Power - - - - 0 - 0 - - - - QComboBox::AdjustToContents - + - Internal + 10 mW - Ext. + Int. + 100 mW - - - - - - Output type - - - - - - - - 0 - 0 - - - - QComboBox::AdjustToContents - - Open Drain + 500 mW - Push Pull + 1000 mW - - - - Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter - - - - - - - Option value - - + + + + + + Bind on startup + + + + + + + Low Power + + + + @@ -352,7 +342,7 @@ - + 16777215 @@ -360,7 +350,7 @@ - Receiver No. + PPM delay Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter @@ -368,46 +358,35 @@ - + 0 0 + + Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter + - + us - 0 + 100 - 63 + 800 - 1 + 50 - 0 + 300 - - - Bind on startup - - - - - - - Low Power - - - - - + 16777215 @@ -415,43 +394,43 @@ - PPM delay + PPM Frame Length Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter - - + + 0 0 - - Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter - - us + ms + + + 1 - 100 + 12.500000000000000 - 800 + 32.500000000000000 - 50 + 0.500000000000000 - 300 + 22.500000000000000 - - + + 16777215 @@ -459,38 +438,77 @@ - PPM Frame Length + Antenna Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter - - + + 0 0 - - ms + + QComboBox::AdjustToContents - - 1 + + + Internal + + + + + Ext. + Int. + + + + + + + + Output type - - 12.500000000000000 + + + + + + + 0 + 0 + - - 32.500000000000000 + + QComboBox::AdjustToContents - - 0.500000000000000 + + + Open Drain + + + + + Push Pull + + + + + + + + Option value - - 22.500000000000000 + + + + + + Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter @@ -560,6 +578,26 @@ + + + Sub Type + + + + + + + + 0 + 0 + + + + QComboBox::AdjustToContents + + + + @@ -575,7 +613,7 @@ - + @@ -613,7 +651,7 @@ - + @@ -629,7 +667,7 @@ - + @@ -667,6 +705,19 @@ + + + + + 0 + 0 + + + + Module Telemetry + + + diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/setup.ui opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/setup.ui --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/setup.ui 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/setup.ui 2017-10-31 16:16:43.000000000 +0000 @@ -6,8 +6,8 @@ 0 0 - 840 - 371 + 893 + 405 @@ -343,16 +343,6 @@ - - - - Qt::LeftToRight - - - Extended Trims - - - @@ -363,40 +353,29 @@ - - - - Qt::LeftToRight - - - Extended Limits - - - - - - - Reverse throttle operation. -If this is checked the throttle will be reversed. Idle will be forward, trim will also be reversed and the throttle warning will be reversed as well. - - - - - Qt::LeftToRight - - - Reverse Throttle - - - - - + + 0 0 + + + Never + + + + + On change + + + + + Always + + @@ -409,6 +388,13 @@ + + + + Global Functions + + + @@ -419,18 +405,15 @@ - - - - Qt::Horizontal - - - - 40 - 20 - + + + + + 0 + 0 + - + @@ -467,38 +450,68 @@ - - + + + + Reverse throttle operation. +If this is checked the throttle will be reversed. Idle will be forward, trim will also be reversed and the throttle warning will be reversed as well. + + + + + Qt::LeftToRight + + + Reverse Throttle + + + + + - + 0 0 - - - Never - - - - - On change - - - - - Always - - + + Edit Checklist... + - - + + + + Qt::LeftToRight + - Global Functions + Extended Trims + + + + + + + Qt::LeftToRight + + + Extended Limits + + + + Qt::Horizontal + + + + 40 + 20 + + + + diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/switchitemmodel.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/switchitemmodel.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/switchitemmodel.cpp 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/switchitemmodel.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -0,0 +1,144 @@ +/* + * Copyright (C) OpenTX + * + * Based on code named + * th9x - http://code.google.com/p/th9x + * er9x - http://code.google.com/p/er9x + * gruvin9x - http://code.google.com/p/gruvin9x + * + * License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + * + * 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. + */ + +#include "switchitemmodel.h" +#include "eeprominterface.h" + +RawSwitchItemModel::RawSwitchItemModel(const GeneralSettings * const generalSettings, const ModelData * const modelData): + generalSettings(generalSettings), + modelData(modelData) +{ + Boards board = Boards(getCurrentBoard()); + Board::Type btype = board.getBoardType(); + Firmware * fw = getCurrentFirmware(); + + // Descending switch direction: NOT (!) switches + if (IS_ARM(btype)) { + add(SWITCH_TYPE_SENSOR, -CPN_MAX_SENSORS); + add(SWITCH_TYPE_TELEMETRY, -1); + add(SWITCH_TYPE_FLIGHT_MODE, -fw->getCapability(FlightModes)); + } + add(SWITCH_TYPE_VIRTUAL, -fw->getCapability(LogicalSwitches)); + add(SWITCH_TYPE_ROTARY_ENCODER, -fw->getCapability(RotaryEncoders)); + add(SWITCH_TYPE_TRIM, -board.getCapability(Board::NumTrimSwitches)); + add(SWITCH_TYPE_MULTIPOS_POT, -(fw->getCapability(MultiposPots) * fw->getCapability(MultiposPotsPositions))); + add(SWITCH_TYPE_SWITCH, -board.getCapability(Board::SwitchPositions)); + + // Ascending switch direction (including zero) + add(SWITCH_TYPE_TIMER_MODE, 5); + add(SWITCH_TYPE_NONE, 1); + add(SWITCH_TYPE_SWITCH, board.getCapability(Board::SwitchPositions)); + add(SWITCH_TYPE_MULTIPOS_POT, fw->getCapability(MultiposPots) * fw->getCapability(MultiposPotsPositions)); + add(SWITCH_TYPE_TRIM, board.getCapability(Board::NumTrimSwitches)); + add(SWITCH_TYPE_ROTARY_ENCODER, fw->getCapability(RotaryEncoders)); + add(SWITCH_TYPE_VIRTUAL, fw->getCapability(LogicalSwitches)); + if (IS_ARM(btype)) { + add(SWITCH_TYPE_FLIGHT_MODE, fw->getCapability(FlightModes)); + add(SWITCH_TYPE_TELEMETRY, 1); + add(SWITCH_TYPE_SENSOR, CPN_MAX_SENSORS); + } + add(SWITCH_TYPE_ON, 1); + add(SWITCH_TYPE_ONE, 1); +} + +void RawSwitchItemModel::add(const RawSwitchType & type, int count) +{ + // Most RawSwitch() indices are one-based (vs. typical zero); these are exceptions to the rule: + const static QVector rawSwitchIndexBaseZeroTypes = QVector() << SWITCH_TYPE_NONE << SWITCH_TYPE_ON << SWITCH_TYPE_OFF << SWITCH_TYPE_TIMER_MODE; + + int rawIdxAdj = 0; + const Board::Type board = getCurrentBoard(); + int i = (count < 0 ? count : 1); + const int maxCount = (i < 0 ? 0 : count + i); + + // handle exceptions in RawSwitch() index values + if (rawSwitchIndexBaseZeroTypes.contains(type)) + rawIdxAdj = -1; + + for ( ; i < maxCount; ++i) { + if (generalSettings) { + if (type == SWITCH_TYPE_SWITCH && IS_HORUS_OR_TARANIS(board) && !generalSettings->switchPositionAllowedTaranis(abs(i))) + continue; + if (type == SWITCH_TYPE_MULTIPOS_POT) { + int pot = div(abs(i) - 1, getCurrentFirmware()->getCapability(MultiposPotsPositions)).quot; + if (!generalSettings->isPotAvailable(pot) || generalSettings->potConfig[pot] != Board::POT_MULTIPOS_SWITCH) + continue; + } + } + RawSwitch rs(type, i + rawIdxAdj); + QStandardItem * modelItem = new QStandardItem(rs.toString(board, generalSettings, modelData)); + modelItem->setData(rs.toValue(), Qt::UserRole); + appendRow(modelItem); + } +} + +void RawSwitchItemModel::update() +{ + for (int i=0; idata(Qt::UserRole).toInt()); + modelItem->setText(swtch.toString(getCurrentBoard(), generalSettings, modelData)); + } +} + +RawSwitchFilterItemModel::RawSwitchFilterItemModel(const GeneralSettings * const generalSettings, const ModelData * const modelData, SwitchContext context): + generalSettings(generalSettings), + modelData(modelData), + context(context), + parent(new RawSwitchItemModel(generalSettings, modelData)) +{ + setSourceModel(parent); + setDynamicSortFilter(false); +} + +bool RawSwitchFilterItemModel::filterAcceptsRow(int sourceRow, const QModelIndex & sourceParent) const +{ + QModelIndex index = sourceModel()->index(sourceRow, 0, sourceParent); + RawSwitch swtch(sourceModel()->data(index, Qt::UserRole).toInt()); + + if (swtch.type == SWITCH_TYPE_FLIGHT_MODE && (context == MixesContext || context == GlobalFunctionsContext)) + return false; + + if (swtch.type == SWITCH_TYPE_VIRTUAL && context == GlobalFunctionsContext) + return false; + + if (swtch.type == SWITCH_TYPE_TIMER_MODE && context != TimersContext) + return false; + + if (swtch.type == SWITCH_TYPE_NONE && context == TimersContext) + return false; + + if (swtch.type == SWITCH_TYPE_SENSOR && context == GlobalFunctionsContext) + return false; + + if ((swtch.type == SWITCH_TYPE_ON || swtch.type == SWITCH_TYPE_ONE) && (context != SpecialFunctionsContext && context != GlobalFunctionsContext)) + return false; + + if (!modelData->isAvailable(swtch)) + return false; + + return true; +} + +void RawSwitchFilterItemModel::update() +{ + parent->update(); + invalidate(); +} diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/switchitemmodel.h opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/switchitemmodel.h --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/switchitemmodel.h 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/switchitemmodel.h 2017-10-31 16:16:43.000000000 +0000 @@ -0,0 +1,58 @@ +/* + * Copyright (C) OpenTX + * + * Based on code named + * th9x - http://code.google.com/p/th9x + * er9x - http://code.google.com/p/er9x + * gruvin9x - http://code.google.com/p/gruvin9x + * + * License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + * + * 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. + */ + +#include +#include +#include "radiodata.h" + +enum SwitchContext +{ + LogicalSwitchesContext, + SpecialFunctionsContext, + GlobalFunctionsContext, + TimersContext, + MixesContext +}; + +class RawSwitchItemModel: public QStandardItemModel { + public: + RawSwitchItemModel(const GeneralSettings * const generalSettings, const ModelData * const modelData); + void update(); + + protected: + void add(const RawSwitchType & type, int count); + + const GeneralSettings * generalSettings; + const ModelData * modelData; +}; + +class RawSwitchFilterItemModel: public QSortFilterProxyModel { + public: + RawSwitchFilterItemModel(const GeneralSettings * const generalSettings = NULL, const ModelData * const modelData = NULL, SwitchContext context = LogicalSwitchesContext); + void update(); + + protected: + const GeneralSettings * generalSettings; + const ModelData * modelData; + SwitchContext context; + RawSwitchItemModel * parent; + + bool filterAcceptsRow(int sourceRow, const QModelIndex & sourceParent) const override; +}; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/telemetry.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/telemetry.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/telemetry.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/telemetry.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -829,24 +829,26 @@ } ui->telemetryProtocol->setCurrentIndex(model->telemetryProtocol); ui->ignoreSensorIds->setField(model->frsky.ignoreSensorIds, this); + ui->disableTelemetryAlarms->setField(model->rssiAlarms.disabled); } else { ui->telemetryProtocolLabel->hide(); ui->telemetryProtocol->hide(); ui->ignoreSensorIds->hide(); + ui->disableTelemetryAlarms->hide(); } - ui->rssiAlarm1SB->setValue(model->frsky.rssiAlarms[0].value); - ui->rssiAlarm2SB->setValue(model->frsky.rssiAlarms[1].value); - if (!IS_HORUS_OR_TARANIS(firmware->getBoard())) { - ui->rssiAlarm1CB->setCurrentIndex(model->frsky.rssiAlarms[0].level); - ui->rssiAlarm2CB->setCurrentIndex(model->frsky.rssiAlarms[1].level); + ui->rssiAlarmWarningSB->setValue(model->rssiAlarms.warning); + ui->rssiAlarmCriticalSB->setValue(model->rssiAlarms.critical); + if (!IS_ARM(firmware->getBoard())) { + ui->rssiAlarmWarningCB->setCurrentIndex(model->rssiAlarms.level[0]); + ui->rssiAlarmCriticalCB->setCurrentIndex(model->rssiAlarms.level[1]); } else { - ui->rssiAlarm1CB->hide(); - ui->rssiAlarm2CB->hide(); - ui->rssiAlarm1Label->setText(tr("Low Alarm")); - ui->rssiAlarm2Label->setText(tr("Critical Alarm")); + ui->rssiAlarmWarningCB->hide(); + ui->rssiAlarmCriticalCB->hide(); + ui->rssiAlarmWarningLabel->setText(tr("Low Alarm")); + ui->rssiAlarmCriticalLabel->setText(tr("Critical Alarm")); } /*if (IS_ARM(firmware->getBoard())) { @@ -1001,27 +1003,27 @@ } } -void TelemetryPanel::on_rssiAlarm1CB_currentIndexChanged(int index) +void TelemetryPanel::on_rssiAlarmWarningCB_currentIndexChanged(int index) { - model->frsky.rssiAlarms[0].level = index; + model->rssiAlarms.level[0] = index; emit modified(); } -void TelemetryPanel::on_rssiAlarm2CB_currentIndexChanged(int index) +void TelemetryPanel::on_rssiAlarmCriticalCB_currentIndexChanged(int index) { - model->frsky.rssiAlarms[1].level = index; + model->rssiAlarms.level[1] = index; emit modified(); } -void TelemetryPanel::on_rssiAlarm1SB_editingFinished() +void TelemetryPanel::on_rssiAlarmWarningSB_editingFinished() { - model->frsky.rssiAlarms[0].value = ui->rssiAlarm1SB->value(); + model->rssiAlarms.warning= ui->rssiAlarmWarningSB->value(); emit modified(); } -void TelemetryPanel::on_rssiAlarm2SB_editingFinished() +void TelemetryPanel::on_rssiAlarmCriticalSB_editingFinished() { - model->frsky.rssiAlarms[1].value = ui->rssiAlarm2SB->value(); + model->rssiAlarms.critical = ui->rssiAlarmCriticalSB->value(); emit modified(); } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/telemetry.h opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/telemetry.h --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/telemetry.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/telemetry.h 2017-10-31 16:16:43.000000000 +0000 @@ -138,10 +138,10 @@ void onModified(); void on_frskyProtoCB_currentIndexChanged(int index); void on_bladesCount_editingFinished(); - void on_rssiAlarm1CB_currentIndexChanged(int index); - void on_rssiAlarm2CB_currentIndexChanged(int index); - void on_rssiAlarm1SB_editingFinished(); - void on_rssiAlarm2SB_editingFinished(); + void on_rssiAlarmWarningCB_currentIndexChanged(int index); + void on_rssiAlarmCriticalCB_currentIndexChanged(int index); + void on_rssiAlarmWarningSB_editingFinished(); + void on_rssiAlarmCriticalSB_editingFinished(); void on_varioLimitMin_DSB_editingFinished(); void on_varioLimitMax_DSB_editingFinished(); void on_varioLimitCenterMin_DSB_editingFinished(); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/telemetry.ui opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/telemetry.ui --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/modeledit/telemetry.ui 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/modeledit/telemetry.ui 2017-10-31 16:16:43.000000000 +0000 @@ -74,30 +74,8 @@ 4 - - - - - 0 - 0 - - - - - 100 - 0 - - - - - - - Alarm 1 - - - - + 0 @@ -126,36 +104,8 @@ - - - - true - - - - 0 - 0 - - - - - - - 20 - - - 80 - - - 1 - - - 50 - - - - - + + 0 @@ -168,13 +118,16 @@ 0 + + + - Alarm 2 + Alarm 1 - + 0 @@ -203,8 +156,27 @@ + + + + + 0 + 0 + + + + + 100 + 0 + + + + Alarm 2 + + + - + true @@ -231,18 +203,33 @@ - - - - Qt::Vertical + + + + true - - - 20 - 0 - + + + 0 + 0 + - + + + + + 20 + + + 80 + + + 1 + + + 50 + + @@ -257,6 +244,26 @@ + + + + Qt::Vertical + + + + 20 + 0 + + + + + + + + Disable telemetry audio warnings + + + @@ -1024,10 +1031,10 @@ telemetryProtocol - rssiAlarm1CB - rssiAlarm1SB - rssiAlarm2CB - rssiAlarm2SB + rssiAlarmWarningCB + rssiAlarmWarningSB + rssiAlarmCriticalCB + rssiAlarmCriticalSB varioSource varioLimitMin_DSB varioLimitCenterMin_DSB diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/modelprinter.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/modelprinter.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/modelprinter.cpp 2017-05-14 17:18:57.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/modelprinter.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -45,6 +45,14 @@ { } +QString ModelPrinter::printBoolean(bool val) +{ + if (val) + return tr("Y"); + else + return tr("N"); +} + void debugHtml(const QString & html) { QFile file("foo.html"); @@ -119,7 +127,9 @@ "PPM16", "PPMsim", "FrSky XJT (D16)", "FrSky XJT (D8)", "FrSky XJT (LR12)", "FrSky DJT", "Crossfire", - "DIY Multiprotocol Module" + "DIY Multiprotocol Module", + "FrSky R9M Module", + "SBUS output at VBat" }; return CHECK_IN_ARRAY(strings, protocol); @@ -130,7 +140,7 @@ static const char *strings[] = { "FlySky", "Hubsan", "FrSky", "Hisky", "V2x2", "DSM", "Devo", "YD717", "KN", "SymaX", "SLT", "CX10", "CG023", "Bayang", "ESky", "MT99XX", "MJXQ", "Shenqi", "FY326", "SFHSS", "J6 PRO","FQ777","Assan","Hontai","OLRS", - "FlySky AFHDS2A", "Q2x2", "Walkera", "Q303", "GW008", "DM002" + "FlySky AFHDS2A", "Q2x2", "Walkera", "Q303", "GW008", "DM002", "CABELL", "Esky 150", "H8 3D" }; if (custom) return "Custom - proto " + QString::number(rfProtocol); @@ -138,7 +148,7 @@ return CHECK_IN_ARRAY(strings, rfProtocol); } -QString ModelPrinter::printMultiSubType(int rfProtocol, bool custom, unsigned int subType) { +QString ModelPrinter::printMultiSubType(unsigned rfProtocol, bool custom, unsigned int subType) { /* custom protocols */ if (custom) @@ -152,6 +162,39 @@ return "???"; } +QString ModelPrinter::printR9MPowerValue(unsigned subType, unsigned val, bool telem) +{ + static const QStringList strFTC = QStringList() << tr("10mW") << tr("100mW") << tr("500mW") << tr("1W"); + static const QStringList strLBT = QStringList() << tr("25mW") << tr("500mW"); + + + if (subType == 0 && (int)val < strFTC.size()) + return strFTC.at(val); + else if (subType == 1) + return (telem ? strLBT.at(0) : strLBT.at(1)); + else + return "???"; +} + +QString ModelPrinter::printModuleSubType(unsigned protocol, unsigned subType, unsigned rfProtocol, bool custom) +{ + static const char * strings[] = { + "FCC", + "LBT(EU)" + }; + + switch (protocol) { + case PULSES_MULTIMODULE: + return printMultiSubType(rfProtocol, custom, subType); + + case PULSES_PXX_R9M: + return CHECK_IN_ARRAY(strings, subType); + + default: + return "???"; + } +} + QString ModelPrinter::printModule(int idx) { const ModuleData &module = model.moduleData[idx]; if (module.protocol == PULSES_OFF) @@ -165,6 +208,8 @@ } if (module.protocol == PULSES_MULTIMODULE) result += " " + tr("radio Protocol %1, subType %2, option value %3").arg(printMultiRfProtocol(module.multi.rfProtocol, module.multi.customProto)).arg(printMultiSubType(module.multi.rfProtocol, module.multi.customProto, module.subType)).arg(module.multi.optionValue); + else if (module.protocol == PULSES_PXX_R9M) + result += " " + tr("Module Type: %1, Power: %2, Telemetry Enabled: %3").arg(printModuleSubType(module.protocol, module.subType)).arg(printR9MPowerValue(module.subType, module.pxx.power, module.pxx.sport_out)).arg(printBoolean(module.pxx.sport_out)); return result; } } @@ -303,7 +348,8 @@ const FlightModeData & fm = model.flightModeData[flightModeIndex]; if (fm.gvars[gvarIndex] <= 1024) { - return QString("%1").arg(fm.gvars[gvarIndex]); + //double val = fm.gvars[gvarIndex] * model.gvarData[gvarIndex].multiplierGet(); + return QString("%1").arg(fm.gvars[gvarIndex] * model.gvarData[gvarIndex].multiplierGet()); } else { int num = fm.gvars[gvarIndex] - 1025; @@ -683,3 +729,80 @@ // qDebug() << "ModelPrinter::createCurveImage()" << idx << filename; return filename; } + +QString ModelPrinter::printGlobalVarUnit(int idx) +{ + return model.gvarData[idx].unitToString().toHtmlEscaped(); +} + +QString ModelPrinter::printGlobalVarPrec(int idx) +{ + return model.gvarData[idx].precToString().toHtmlEscaped(); +} + +QString ModelPrinter::printGlobalVarMin(int idx) +{ + return QString::number(model.gvarData[idx].getMinPrec()); +} + +QString ModelPrinter::printGlobalVarMax(int idx) +{ + return QString::number(model.gvarData[idx].getMaxPrec()); +} + +QString ModelPrinter::printGlobalVarPopup(int idx) +{ + return printBoolean(model.gvarData[idx].popup); +} + +QString ModelPrinter::printOutputValueGVar(int val) +{ + QString result = ""; + if (abs(val) > 10000) { + if (val < 0) + result = "-"; + result.append(RawSource(SOURCE_TYPE_GVAR, abs(val)-10001).toString(&model)); + } + else { + if (val >= 0) + result = "+"; + result.append(QString::number((qreal)val/10, 'f', 1) + "%"); + } + return result; +} + +QString ModelPrinter::printOutputOffset(int idx) +{ + return printOutputValueGVar(model.limitData[idx].offset); +} + +QString ModelPrinter::printOutputMin(int idx) +{ + return printOutputValueGVar(model.limitData[idx].min); +} + +QString ModelPrinter::printOutputMax(int idx) +{ + return printOutputValueGVar(model.limitData[idx].max); +} + +QString ModelPrinter::printOutputRevert(int idx) +{ + return model.limitData[idx].revertToString(); +} + +QString ModelPrinter::printOutputPpmCenter(int idx) +{ + return QString::number(model.limitData[idx].ppmCenter + 1500); +} + +QString ModelPrinter::printOutputCurve(int idx) +{ + return CurveReference(CurveReference::CURVE_REF_CUSTOM, model.limitData[idx].curve.value).toString(&model, false); +} + +QString ModelPrinter::printOutputSymetrical(int idx) +{ + return printBoolean(model.limitData[idx].symetrical); +} + diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/modelprinter.h opentx-companion22-2.2.1~ppa01~xenial/companion/src/modelprinter.h --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/modelprinter.h 2017-04-29 16:57:04.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/modelprinter.h 2017-12-17 16:22:27.000000000 +0000 @@ -54,12 +54,15 @@ ModelPrinter(Firmware * firmware, const GeneralSettings & generalSettings, const ModelData & model); virtual ~ModelPrinter(); + QString printBoolean(bool val); QString printEEpromSize(); QString printTrimIncrementMode(); QString printThrottleTrimMode(); static QString printModuleProtocol(unsigned int protocol); static QString printMultiRfProtocol(int rfProtocol, bool custom); - static QString printMultiSubType(int rfProtocol, bool custom, unsigned int subType); + static QString printR9MPowerValue(unsigned subType, unsigned val, bool telem); + static QString printMultiSubType(unsigned rfProtocol, bool custom, unsigned int subType); + static QString printModuleSubType(unsigned protocol, unsigned subType, unsigned rfProtocol = 0, bool custom = false); QString printFlightModeSwitch(const RawSwitch & swtch); QString printFlightModeName(int index); QString printFlightModes(unsigned int flightModes); @@ -82,6 +85,19 @@ QString printCurveName(int idx); QString printCurve(int idx); QString createCurveImage(int idx, QTextDocument * document); + QString printGlobalVarUnit(int idx); + QString printGlobalVarPrec(int idx); + QString printGlobalVarMin(int idx); + QString printGlobalVarMax(int idx); + QString printGlobalVarPopup(int idx); + QString printOutputValueGVar(int val); + QString printOutputOffset(int idx); + QString printOutputMin(int idx); + QString printOutputMax(int idx); + QString printOutputRevert(int idx); + QString printOutputCurve(int idx); + QString printOutputPpmCenter(int idx); + QString printOutputSymetrical(int idx); private: Firmware * firmware; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/multimodelprinter.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/multimodelprinter.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/multimodelprinter.cpp 2017-04-29 16:57:04.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/multimodelprinter.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -162,7 +162,7 @@ str += printFlightModes(); str += printInputs(); str += printMixers(); - str += printLimits(); + str += printOutputs(); str += printCurves(document); if (firmware->getCapability(Gvars) && !firmware->getCapability(GvarsFlightModes)) str += printGvars(); @@ -307,18 +307,64 @@ if ((gvars && firmware->getCapability(GvarsFlightModes)) || firmware->getCapability(RotaryEncoders)) { MultiColumns columns(modelPrinterMap.size()); columns.append(""); - columns.append(""); + columns.append(""); if (firmware->getCapability(GvarsFlightModes)) { for (int i=0; i" + tr("GV%1").arg(i+1) + "
"); - COMPARE(model->gvars_names[i]); - columns.append(""); + columns.append("
"); } } for (int i=0; igetCapability(RotaryEncoders); i++) { columns.append(""); } columns.append(""); + + if (firmware->getCapability(GvarsFlightModes)) { + columns.append(""); + for (int i=0; i"); + COMPARE(model->gvarData[i].name); + columns.append(""); + } + columns.append(""); + columns.append(""); + for (int i=0; i"); + COMPARE(modelPrinter->printGlobalVarUnit(i)); + columns.append(""); + } + columns.append(""); + columns.append(""); + for (int i=0; i"); + COMPARE(modelPrinter->printGlobalVarPrec(i)); + columns.append(""); + } + columns.append(""); + columns.append(""); + for (int i=0; i"); + COMPARE(modelPrinter->printGlobalVarMin(i)); + columns.append(""); + } + columns.append(""); + columns.append(""); + for (int i=0; i"); + COMPARE(modelPrinter->printGlobalVarMax(i)); + columns.append(""); + } + columns.append(""); + columns.append(""); + for (int i=0; i"); + COMPARE(modelPrinter->printGlobalVarPopup(i)); + columns.append(""); + } + columns.append(""); + } + + columns.append(""); + for (int i=0; igetCapability(FlightModes); i++) { columns.append("
" + tr("Flight mode") + "
" + tr("Global variables") + "" + tr("GV%1").arg(i+1) + "" + tr("RE%1").arg(i+1) + "
Name
Unit
Prec
Min
Max
Popup
" + tr("Flight mode") + "
" + tr("FM%1").arg(i) + " "); COMPARE(model->flightModeData[i].name); @@ -344,18 +390,24 @@ return str; } -QString MultiModelPrinter::printLimits() +QString MultiModelPrinter::printOutputs() { - QString str = printTitle(tr("Limits")); + QString str = printTitle(tr("Outputs")); MultiColumns columns(modelPrinterMap.size()); columns.append("" \ "" \ - " " \ - " " \ - " " \ - " " \ - " " \ - ""); + "" \ + "" \ + "" \ + "" \ + ""); + if (IS_HORUS_OR_TARANIS(firmware->getBoard())) + columns.append(" "); + if (firmware->getCapability(PPMCenter)) + columns.append(" "); + if (firmware->getCapability(SYMLimits)) + columns.append(" "); + columns.append(""); for (int i=0; igetCapability(Outputs); i++) { int count = 0; for (int k=0; k < modelPrinterMap.size(); k++) @@ -365,15 +417,30 @@ columns.append(""); - + COMPARE(modelPrinter->printOutputRevert(i)); + columns.append(""); + if (IS_HORUS_OR_TARANIS(firmware->getBoard())) { + columns.append(""); + } + if (firmware->getCapability(PPMCenter)) { + columns.append(""); + } + if (firmware->getCapability(SYMLimits)) { + columns.append(""); + } + columns.append(""); } columns.append("
" + tr("Channel") + "" + tr("Offset") + "" + tr("Min") + "" + tr("Max") + "" + tr("Invert") + "
" + tr("Channel") + "" + tr("Subtrim") + "" + tr("Min") + "" + tr("Max") + "" + tr("Direct") + "" + tr("Curve") + "" + tr("PPM") + "" + tr("Linear") + "
"); COMPARE(modelPrinter->printChannelName(i)); columns.append(""); - COMPARE(model->limitData[i].offsetToString()); + COMPARE(modelPrinter->printOutputOffset(i)); columns.append(""); - COMPARE(model->limitData[i].minToString()); + COMPARE(modelPrinter->printOutputMin(i)); columns.append(""); - COMPARE(model->limitData[i].maxToString()); + COMPARE(modelPrinter->printOutputMax(i)); columns.append(""); - COMPARE(model->limitData[i].revertToString()); - columns.append("
"); + COMPARE(modelPrinter->printOutputCurve(i)); + columns.append(""); + COMPARE(modelPrinter->printOutputPpmCenter(i)); + columns.append(""); + COMPARE(modelPrinter->printOutputSymetrical(i)); + columns.append("
"); str.append(columns.print()); @@ -572,14 +639,19 @@ columns.append(""); for (int i=0; i<2; i++) { columns.append(""); } columns.append("
" + QString(i==0 ? tr("RSSI Alarms") : "") + ""); - if (IS_HORUS_OR_TARANIS(getCurrentBoard())) { + if (IS_ARM(getCurrentBoard())) { COMPARE(i==0 ? tr("Low Alarm") : tr("Critical Alarm")); } else { - COMPARE(getFrSkyAlarmType(model->frsky.rssiAlarms[i].level)); + COMPARE(getFrSkyAlarmType(model->rssiAlarms.level[i])); } columns.append("<"); - COMPARE(QString::number(model->frsky.rssiAlarms[i].value, 10)); + if (i == 0) { + COMPARE(QString::number(model->rssiAlarms.warning, 10)); + } + else { + COMPARE(QString::number(model->rssiAlarms.critical, 10)); + } columns.append("

"); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/multimodelprinter.h opentx-companion22-2.2.1~ppa01~xenial/companion/src/multimodelprinter.h --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/multimodelprinter.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/multimodelprinter.h 2017-12-17 16:22:27.000000000 +0000 @@ -66,7 +66,7 @@ QString printSetup(); QString printHeliSetup(); QString printFlightModes(); - QString printLimits(); + QString printOutputs(); QString printInputs(); QString printMixers(); QString printCurves(QTextDocument * document); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/multiprotocols.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/multiprotocols.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/multiprotocols.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/multiprotocols.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -45,8 +45,8 @@ static const QStringList STR_SUBTYPE_SYMAX {"Standard", "Syma X5C"}; static const QStringList STR_SUBTYPE_SLT {"SLT", "Vista"}; static const QStringList STR_SUBTYPE_CX10 {"Green", "Blue", "DM007", "-", "JC3015a", "JC3015b", "MK33041", "Q242"}; -static const QStringList STR_SUBTYPE_CG023 {"CG023", "YD829", "H8 3D"}; -static const QStringList STR_SUBTYPE_BAYANG {"Bayang", "H8S3D"}; +static const QStringList STR_SUBTYPE_CG023 {"CG023", "YD829"}; +static const QStringList STR_SUBTYPE_BAYANG {"Bayang", "H8S3D", "X16 AH", "IRDRONE"}; static const QStringList STR_SUBTYPE_KN {"WLtoys", "FeiLun"}; static const QStringList STR_SUBTYPE_MT99 {"MT99", "H7", "YZ", "LS", "FY805"}; static const QStringList STR_SUBTYPE_MJXQ {"WLH08", "X600", "X800", "H26D", "E010", "H26WH"}; @@ -56,39 +56,43 @@ static const QStringList STR_SUBTYPE_Q2X2 {"Q222", "Q242", "Q282"}; static const QStringList STR_SUBTYPE_WK2x01 {"WK2801", "WK2401", "W6_5_1", "W6_6_1", "W6_HEL", "W6_HEL_I"}; static const QStringList STR_SUBTYPE_Q303 {"Q303", "CX35", "CX10D", "CX10WD"}; +static const QStringList STR_SUBTYPE_CABELL {"CABELL V3","C TELEM","-","-","-","-","F_SAFE","UNBIND"}; +static const QStringList STR_SUBTYPE_H83D {"H8_3D","H20H","H20Mini","H30Mini"}; static const QStringList NO_SUBTYPE {STR_MULTI_DEFAULT}; // Table is designed to be shared with gui_common_arm.cpp const Multiprotocols multiProtocols { - { MM_RF_PROTO_FLYSKY, STR_SUBTYPE_FLYSKY, 4, nullptr }, - { MM_RF_PROTO_HUBSAN, NO_SUBTYPE, 0, STR_MULTI_VIDFREQ }, - { MM_RF_PROTO_FRSKY, STR_SUBTYPE_FRSKY, 5, STR_MULTI_RFTUNE }, - { MM_RF_PROTO_HISKY, STR_SUBTYPE_HISKY, 1, nullptr }, - { MM_RF_PROTO_V2X2, STR_SUBTYPE_V2X2, 1, nullptr }, - { MM_RF_PROTO_DSM2, STR_SUBTYPE_DSM, 3, nullptr }, - { MM_RF_PROTO_YD717, STR_SUBTYPE_YD717, 4, nullptr }, - { MM_RF_PROTO_KN, STR_SUBTYPE_KN, 1, nullptr }, - { MM_RF_PROTO_SYMAX, STR_SUBTYPE_SYMAX, 1, nullptr }, - { MM_RF_PROTO_SLT, STR_SUBTYPE_SLT, 1, nullptr }, - { MM_RF_PROTO_CX10, STR_SUBTYPE_CX10, 7, nullptr }, - { MM_RF_PROTO_CG023, STR_SUBTYPE_CG023, 2, nullptr }, - { MM_RF_PROTO_BAYANG, STR_SUBTYPE_BAYANG, 1, STR_MULTI_TELEMETRY }, - { MM_RF_PROTO_MT99XX, STR_SUBTYPE_MT99, 4, nullptr }, - { MM_RF_PROTO_MJXQ, STR_SUBTYPE_MJXQ, 5, nullptr }, - { MM_RF_PROTO_FY326, STR_SUBTYPE_FY326, 1, nullptr }, - { MM_RF_PROTO_SFHSS, NO_SUBTYPE, 0, STR_MULTI_RFTUNE }, - { MM_RF_PROTO_HONTAI, STR_SUBTYPE_HONTAI, 2, nullptr }, - { MM_RF_PROTO_OLRS, NO_SUBTYPE, 0, STR_MULTI_RFPOWER }, - { MM_RF_PROTO_FS_AFHDS2A, STR_SUBTYPE_AFHDS2A, 3, STR_MULTI_SERVOFREQ }, - { MM_RF_PROTO_Q2X2, STR_SUBTYPE_Q2X2, 2, nullptr }, - { MM_RF_PROTO_WK_2X01, STR_SUBTYPE_WK2x01, 5, nullptr }, - { MM_RF_PROTO_Q303, STR_SUBTYPE_Q303, 3, nullptr }, - { MM_RF_CUSTOM_SELECTED, STR_SUBTYPE_CUSTOM, 7, STR_MULTI_OPTION }, + {MM_RF_PROTO_FLYSKY, 4, false, STR_SUBTYPE_FLYSKY, nullptr}, + {MM_RF_PROTO_HUBSAN, 0, false, NO_SUBTYPE, STR_MULTI_VIDFREQ}, + {MM_RF_PROTO_FRSKY, 5, false, STR_SUBTYPE_FRSKY, STR_MULTI_RFTUNE}, + {MM_RF_PROTO_HISKY, 1, false, STR_SUBTYPE_HISKY, nullptr}, + {MM_RF_PROTO_V2X2, 1, false, STR_SUBTYPE_V2X2, nullptr}, + {MM_RF_PROTO_DSM2, 3, false, STR_SUBTYPE_DSM, nullptr}, + {MM_RF_PROTO_YD717, 4, false, STR_SUBTYPE_YD717, nullptr}, + {MM_RF_PROTO_KN, 1, false, STR_SUBTYPE_KN, nullptr}, + {MM_RF_PROTO_SYMAX, 1, false, STR_SUBTYPE_SYMAX, nullptr}, + {MM_RF_PROTO_SLT, 1, false, STR_SUBTYPE_SLT, nullptr}, + {MM_RF_PROTO_CX10, 7, false, STR_SUBTYPE_CX10, nullptr}, + {MM_RF_PROTO_CG023, 1, false, STR_SUBTYPE_CG023, nullptr}, + {MM_RF_PROTO_BAYANG, 3, false, STR_SUBTYPE_BAYANG, STR_MULTI_TELEMETRY}, + {MM_RF_PROTO_MT99XX, 4, false, STR_SUBTYPE_MT99, nullptr}, + {MM_RF_PROTO_MJXQ, 5, false, STR_SUBTYPE_MJXQ, nullptr}, + {MM_RF_PROTO_FY326, 1, false, STR_SUBTYPE_FY326, nullptr}, + {MM_RF_PROTO_SFHSS, 0, true, NO_SUBTYPE, STR_MULTI_RFTUNE}, + {MM_RF_PROTO_HONTAI, 2, false, STR_SUBTYPE_HONTAI, nullptr}, + {MM_RF_PROTO_OLRS, 0, false, NO_SUBTYPE, STR_MULTI_RFPOWER}, + {MM_RF_PROTO_FS_AFHDS2A, 3, true, STR_SUBTYPE_AFHDS2A, STR_MULTI_SERVOFREQ}, + {MM_RF_PROTO_Q2X2, 2, false, STR_SUBTYPE_Q2X2, nullptr}, + {MM_RF_PROTO_WK_2X01, 5, false, STR_SUBTYPE_WK2x01, nullptr}, + {MM_RF_PROTO_Q303, 3, false, STR_SUBTYPE_Q303, nullptr}, + {MM_RF_PROTO_CABELL, 7, false, STR_SUBTYPE_CABELL, STR_MULTI_OPTION}, + {MM_RF_PROTO_H83D, 3, false, STR_SUBTYPE_H83D, nullptr}, + {MM_RF_CUSTOM_SELECTED, 7, true, STR_SUBTYPE_CUSTOM, STR_MULTI_OPTION}, - //Sential and default for protocols not listed above (MM_RF_CUSTOM is 0xff() - { 0xfe, NO_SUBTYPE, 0, nullptr } + // Sentinel and default for protocols not listed above (MM_RF_CUSTOM is 0xff) + { 0xfe, 0, false, NO_SUBTYPE, nullptr} }; int Multiprotocols::MultiProtocolDefinition::getOptionMin() const { diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/multiprotocols.h opentx-companion22-2.2.1~ppa01~xenial/companion/src/multiprotocols.h --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/multiprotocols.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/multiprotocols.h 2017-11-11 11:29:14.000000000 +0000 @@ -34,13 +34,15 @@ struct radio_mm_definition { int protocol; - QStringList protocols; unsigned int maxSubtype; + bool hasFailsafe; + QStringList protocols; QString optionsstr; }; struct MultiProtocolDefinition { const int protocol; + const bool hasFailsafe; const QStringList subTypeStrings; const QString optionsstr; @@ -55,6 +57,7 @@ MultiProtocolDefinition(const radio_mm_definition &rd) : protocol(rd.protocol), + hasFailsafe(rd.hasFailsafe), subTypeStrings(rd.protocols), optionsstr(rd.optionsstr) { diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/radiodata.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/radiodata.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/radiodata.cpp 2017-04-29 16:57:04.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/radiodata.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -31,7 +31,7 @@ } if (IS_HORUS(after)) { - if (IS_TARANIS_X9D(before) || IS_TARANIS_X7(before)) { + if (IS_TARANIS_X9D(before)) { if (type == SOURCE_TYPE_STICK && index >= 7) { // LS and RS on Horus are after sliders L1 and L2 index += 2; @@ -46,47 +46,90 @@ } } - // No SE and SG on X7 board if (IS_TARANIS_X7(after)) { - if (IS_TARANIS_X9(before) || IS_HORUS(before)) { - if (type == SOURCE_TYPE_SWITCH && index >= 6) { - index -= 2; + // No S3, LS and RS on X7 board + if (type == SOURCE_TYPE_STICK && index >= 6) { + index = 5; + } + + // No SE and SG on X7 board + if ((IS_TARANIS_X9(before) || IS_HORUS(before)) && type == SOURCE_TYPE_SWITCH) { + if (index == 4 || index == 6) { + index = 3; // SG and SE to SD + } + else if (index == 5) { + index = 4; // SF to SF } - else if (type == SOURCE_TYPE_SWITCH && index >= 4) { - index -= 1; + else if (index == 7) { + index = 5; // SH to SH } } } + // Compensate for SE and SG on X9/Horus board if converting from X7 + if ((IS_TARANIS_X9(after) || IS_HORUS(after)) && IS_TARANIS_X7(before) && type == SOURCE_TYPE_SWITCH) { + if (index == 4) { + index = 5; // SF to SF + } + else if (index == 5) { + index = 7; // SH to SH + } + } + return *this; } RawSwitch RawSwitch::convert(Board::Type before, Board::Type after) { + if (!index || type != SWITCH_TYPE_SWITCH) { + return *this; // no changes + } + // SWI to SWR don't exist on !X9E board if (!IS_TARANIS_X9E(after) && IS_TARANIS_X9E(before)) { - if (type == SWITCH_TYPE_SWITCH && index >= 24) { + if (abs(index) > 24) { index = index % 24; } } + int srcIdx = div(abs(index)-1, 3).quot; // raw source index + int delta = 0; + // No SE and SG on X7 board - if (IS_TARANIS_X7(after)) { - if (IS_TARANIS_X9(before) || IS_HORUS(before)) { - if (type == SWITCH_TYPE_SWITCH && index >= 18) { - index -= 6; - } - else if (type == SWITCH_TYPE_SWITCH && index >= 12) { - index -= 3; - } + if (IS_TARANIS_X7(after) && (IS_TARANIS_X9(before) || IS_HORUS(before))) { + if (srcIdx == 4 || srcIdx == 5) { + delta = 3; // SE to SD & SF to SF + } + else if (srcIdx == 6) { + delta = 9; // SG to SD + } + else if (srcIdx == 7) { + delta = 6; // SH to SH + } + } + + // Compensate for SE and SG on X9/Horus board if converting from X7 + if ((IS_TARANIS_X9(after) || IS_HORUS(after)) && IS_TARANIS_X7(before)) { + if (srcIdx == 4) { + delta = -3; // SF to SF + } + else if (srcIdx == 5) { + delta = -6; // SH to SH } } + if (index < 0) { + delta = -delta; // invert for !switch + } + + index -= delta; + return *this; } void ExpoData::convert(Board::Type before, Board::Type after) { + srcRaw.convert(before, after); swtch.convert(before, after); } @@ -125,6 +168,8 @@ void CustomFunctionData::convert(Board::Type before, Board::Type after) { swtch.convert(before, after); + if (func == FuncVolume || func == FuncPlayValue || (func >= FuncAdjustGV1 && func <= FuncAdjustGVLast && adjustMode == 1)) + param = RawSource(param).convert(before, after).toValue(); } void FlightModeData::convert(Board::Type before, Board::Type after) @@ -160,6 +205,10 @@ { // Here we can add explicit conversions when moving from one board to another + for (int i=0; igetCapability(MinContrast); + unsigned int max_contrast = getCurrentFirmware()->getCapability(MaxContrast); + + if (contrast < min_contrast) + contrast = min_contrast; + else if (contrast > max_contrast) + contrast = max_contrast; + } } @@ -254,4 +313,9 @@ if (IS_HORUS(after)) { fixModelFilenames(); } + + // ensure proper number of model slots + if (getCurrentFirmware()->getCapability(Models) && getCurrentFirmware()->getCapability(Models) != (int)models.size()) { + models.resize(getCurrentFirmware()->getCapability(Models)); + } } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/radiodata.h opentx-companion22-2.2.1~ppa01~xenial/companion/src/radiodata.h --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/radiodata.h 2017-04-29 16:57:04.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/radiodata.h 2017-12-17 16:22:27.000000000 +0000 @@ -250,7 +250,9 @@ SWITCH_TYPE_OFF, SWITCH_TYPE_ONE, SWITCH_TYPE_FLIGHT_MODE, - SWITCH_TYPE_TIMER_MODE + SWITCH_TYPE_TIMER_MODE, + SWITCH_TYPE_TELEMETRY, + SWITCH_TYPE_SENSOR, }; class RawSwitch { @@ -278,7 +280,7 @@ return index >= 0 ? (type * 256 + index) : -(type * 256 - index); } - QString toString(Board::Type board = Board::BOARD_UNKNOWN, const GeneralSettings * const generalSettings = NULL) const; + QString toString(Board::Type board = Board::BOARD_UNKNOWN, const GeneralSettings * const generalSettings = NULL, const ModelData * const modelData = NULL) const; bool operator== ( const RawSwitch& other) { return (this->type == other.type) && (this->index == other.index); @@ -591,12 +593,20 @@ void clear() { memset(this, 0, sizeof(FrSkyAlarmData)); } }; -class FrSkyRSSIAlarm { +class RSSIAlarmData { public: - FrSkyRSSIAlarm() { clear(0, 50); } - unsigned int level; - int value; - void clear(unsigned int level, int value) { this->level = level; this->value = value;} + RSSIAlarmData() { clear(); } + unsigned int level[2]; // AVR Only + int warning; + int critical; + bool disabled; + void clear() { + this->level[0] = 2; + this->level[1] = 3; + this->warning = 45; + this->critical = 42; + this->disabled = false; + } }; class FrSkyChannelData { @@ -615,8 +625,8 @@ struct FrSkyBarData { RawSource source; - unsigned int barMin; // minimum for bar display - unsigned int barMax; // ditto for max display (would usually = ratio) + int barMin; // minimum for bar display + int barMax; // ditto for max display (would usually = ratio) }; struct FrSkyLineData { @@ -703,7 +713,6 @@ unsigned int altitudeSource; unsigned int currentSource; FrSkyScreenData screens[4]; - FrSkyRSSIAlarm rssiAlarms[2]; unsigned int varioSource; bool varioCenterSilent; int varioMin; @@ -765,6 +774,8 @@ PULSES_PXX_DJT, PULSES_CROSSFIRE, PULSES_MULTIMODULE, + PULSES_PXX_R9M, + PULSES_SBUS, PULSES_PROTOCOL_LAST }; @@ -801,7 +812,10 @@ MM_RF_PROTO_Q303, MM_RF_PROTO_GW008, MM_RF_PROTO_DM002, - MM_RF_PROTO_LAST=MM_RF_PROTO_DM002 + MM_RF_PROTO_CABELL, + MM_RF_PROTO_ESKY150, + MM_RF_PROTO_H83D, + MM_RF_PROTO_LAST=MM_RF_PROTO_H83D }; enum TrainerProtocol { @@ -840,6 +854,13 @@ int optionValue; } multi; + struct { + int power; // 0 10 mW, 1 100 mW, 2 500 mW, 3 1W + bool receiver_telem_off; // false = receiver telem enabled + bool receiver_channel_9_16; // false = pwm out 1-8, true 9-16 + bool external_antenna; // false = internal antenna, true = external antenna + bool sport_out; + } pxx; void clear() { memset(this, 0, sizeof(ModuleData)); } @@ -1006,6 +1027,44 @@ typedef char TopbarData[216+1]; #endif +#define GVAR_NAME_LEN 3 +#define GVAR_MAX_VALUE 1024 +#define GVAR_MIN_VALUE -GVAR_MAX_VALUE + +class GVarData { + public: + GVarData() { clear(); } + + enum { + GVAR_UNIT_NUMBER, + GVAR_UNIT_PERCENT + }; + + enum { + GVAR_PREC_MUL10, + GVAR_PREC_MUL1 + }; + + char name[GVAR_NAME_LEN+1]; + int min; + int max; + bool popup; + unsigned int prec; // 0 0._ 1 0.0 + unsigned int unit; // 0 _ 1 % + + void clear() {memset(this, 0, sizeof(GVarData)); } + QString unitToString() const; + QString precToString() const; + int multiplierSet(); + float multiplierGet() const; + void setMin(float val); + void setMax(float val); + int getMin() const; + int getMax() const; + float getMinPrec() const; + float getMaxPrec() const; +}; + class ModelData { public: ModelData(); @@ -1060,12 +1119,11 @@ bool potsWarningEnabled[CPN_MAX_POTS]; int potPosition[CPN_MAX_POTS]; bool displayChecklist; - // TODO structure - char gvars_names[CPN_MAX_GVARS][6+1]; - bool gvars_popups[CPN_MAX_GVARS]; + GVarData gvarData[CPN_MAX_GVARS]; MavlinkData mavlink; unsigned int telemetryProtocol; FrSkyData frsky; + RSSIAlarmData rssiAlarms; char bitmap[10+1]; @@ -1094,6 +1152,7 @@ bool isGVarLinked(int phaseIdx, int gvarIdx); int getGVarFieldValue(int phaseIdx, int gvarIdx); + float getGVarFieldValuePrec(int phaseIdx, int gvarIdx); ModelData removeGlobalVars(); @@ -1102,6 +1161,8 @@ int getChannelsMax(bool forceExtendedLimits=false) const; + bool isAvailable(const RawSwitch & swtch) const; + protected: void removeGlobalVar(int & var); }; @@ -1160,11 +1221,11 @@ unsigned int view; // main screen view // TODO enum bool disableThrottleWarning; bool fai; - int switchWarning; // -1=down, 0=off, 1=up bool disableMemoryWarning; BeeperMode beeperMode; bool disableAlarmWarning; - bool enableTelemetryAlarm; + bool disableRssiPoweroffAlarm; + unsigned int usbMode; BeeperMode hapticMode; unsigned int stickMode; // TODO enum int timezone; @@ -1199,7 +1260,8 @@ unsigned int globalTimer; bool bluetoothEnable; char bluetoothName[10+1]; - unsigned int btBaudrate; + unsigned int bluetoothBaudrate; + unsigned int bluetoothMode; unsigned int sticksGain; unsigned int rotarySteps; unsigned int countryCode; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/simulation/CMakeLists.txt opentx-companion22-2.2.1~ppa01~xenial/companion/src/simulation/CMakeLists.txt --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/simulation/CMakeLists.txt 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/simulation/CMakeLists.txt 2017-11-20 18:44:06.000000000 +0000 @@ -7,6 +7,7 @@ simulateduiwidgetX7.cpp simulateduiwidgetX9.cpp simulateduiwidgetX9E.cpp + simulateduiwidgetX10.cpp simulateduiwidgetX12.cpp simulatorinterface.cpp simulatormainwindow.cpp @@ -25,6 +26,7 @@ simulateduiwidgetX7.ui simulateduiwidgetX9.ui simulateduiwidgetX9E.ui + simulateduiwidgetX10.ui simulateduiwidgetX12.ui simulatormainwindow.ui simulatorstartupdialog.ui diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/simulation/debugoutput.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/simulation/debugoutput.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/simulation/debugoutput.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/simulation/debugoutput.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -94,8 +94,11 @@ connect(ui->actionToggleFilter, &QAction::toggled, this, &DebugOutput::onFilterToggled); connect(ui->filterText, &QComboBox::currentTextChanged, this, &DebugOutput::onFilterTextChanged); - if (AppDebugMessageHandler::instance()) - connect(AppDebugMessageHandler::instance(), &AppDebugMessageHandler::messageOutput, this, &DebugOutput::onAppDebugMessage); + if (AppDebugMessageHandler::instance()) { + // send application Info/Warning/Error events to our data collector + m_dataBufferDevice->setProperty("level", 1); + AppDebugMessageHandler::instance()->addOutputDevice(m_dataBufferDevice); + } // send firmware TRACE events to our data collector m_simulator->addTracebackDevice(m_dataBufferDevice); @@ -103,10 +106,9 @@ DebugOutput::~DebugOutput() { - if (AppDebugMessageHandler::instance()) - disconnect(AppDebugMessageHandler::instance(), 0, this, 0); - if (m_dataBufferDevice) { + if (AppDebugMessageHandler::instance()) + AppDebugMessageHandler::instance()->removeOutputDevice(m_dataBufferDevice); m_simulator->removeTracebackDevice(m_dataBufferDevice); disconnect(m_dataBufferDevice, 0, this, 0); disconnect(this, 0, m_dataBufferDevice, 0); @@ -201,13 +203,6 @@ } } -void DebugOutput::onAppDebugMessage(quint8 level, const QString & msg) -{ - if (level > 0 && m_dataBufferDevice) { - m_dataBufferDevice->write(qPrintable(msg % "\n")); - } -} - /* * UI handlers */ diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/simulation/debugoutput.h opentx-companion22-2.2.1~ppa01~xenial/companion/src/simulation/debugoutput.h --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/simulation/debugoutput.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/simulation/debugoutput.h 2017-10-31 16:16:43.000000000 +0000 @@ -72,7 +72,6 @@ void restoreState(); void processBytesReceived(); void onDataBufferOverflow(const qint64 len); - void onAppDebugMessage(quint8 level, const QString & msg); void onFilterStateChanged(); void onFilterTextChanged(const QString &); void onFilterToggled(bool enable); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/simulation/radiooutputswidget.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/simulation/radiooutputswidget.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/simulation/radiooutputswidget.cpp 2017-05-14 17:18:57.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/simulation/radiooutputswidget.cpp 2017-11-20 18:44:06.000000000 +0000 @@ -305,13 +305,15 @@ QHash fmMap = m_globalVarsMap.value(index); SimulatorInterface::gVarMode_t gv(value); + QLabel * lbl; - if (fmMap.contains(gv.mode)) { - QLabel * lbl = fmMap.value(gv.mode); - if (lbl) - lbl->setText(QString::number(gv.value)); + if (fmMap.contains(gv.mode) && (lbl = fmMap.value(gv.mode))) { + GVarData gvar; + gvar.prec = gv.prec; + gvar.unit = gv.unit; + lbl->setText(QString::number(gv.value * gvar.multiplierGet(), 'f', gv.prec) + gvar.unitToString()); } - //qDebug() << index << value << gv.mode << gv.value; + //qDebug() << index << value << gv.mode << gv.value << gv.prec << gv.unit; } void RadioOutputsWidget::onPhaseChanged(qint32 phase, const QString &) diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/simulation/simulateduiwidget.h opentx-companion22-2.2.1~ppa01~xenial/companion/src/simulation/simulateduiwidget.h --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/simulation/simulateduiwidget.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/simulation/simulateduiwidget.h 2017-11-20 18:44:06.000000000 +0000 @@ -107,6 +107,7 @@ class SimulatedUIWidgetX7; class SimulatedUIWidgetX9; class SimulatedUIWidgetX9E; + class SimulatedUIWidgetX10; class SimulatedUIWidgetX12; } @@ -162,6 +163,18 @@ Ui::SimulatedUIWidgetX9E * ui; }; +class SimulatedUIWidgetX10: public SimulatedUIWidget +{ + Q_OBJECT + + public: + explicit SimulatedUIWidgetX10(SimulatorInterface * simulator, QWidget * parent = NULL); + virtual ~SimulatedUIWidgetX10(); + + private: + Ui::SimulatedUIWidgetX10 * ui; +}; + class SimulatedUIWidgetX12: public SimulatedUIWidget { Q_OBJECT diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/simulation/simulateduiwidgetX10.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/simulation/simulateduiwidgetX10.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/simulation/simulateduiwidgetX10.cpp 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/simulation/simulateduiwidgetX10.cpp 2017-11-20 18:44:06.000000000 +0000 @@ -0,0 +1,78 @@ +/* + * Copyright (C) OpenTX + * + * Based on code named + * th9x - http://code.google.com/p/th9x + * er9x - http://code.google.com/p/er9x + * gruvin9x - http://code.google.com/p/gruvin9x + * + * License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + * + * 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. + */ + +#include "simulateduiwidget.h" +#include "ui_simulateduiwidgetX10.h" + +SimulatedUIWidgetX10::SimulatedUIWidgetX10(SimulatorInterface *simulator, QWidget * parent): + SimulatedUIWidget(simulator, parent), + ui(new Ui::SimulatedUIWidgetX10) +{ + RadioUiAction * act; + QPolygon polygon; + + ui->setupUi(this); + + // add actions in order of appearance on the help menu + + int x = 74, y = 148, oR = 63, iR = 40; + + polygon.clear(); + polygon << polyArc(x, y, oR, -45, 45) << polyArc(x, y, iR, -45, 45); + act = new RadioUiAction(3, QList() << Qt::Key_Up, SIMU_STR_HLP_KEY_UP, SIMU_STR_HLP_ACT_MDL); + addRadioWidget(ui->leftbuttons->addArea(polygon, "X10/left_mdl.png", act)); + + polygon.clear(); + polygon << polyArc(x, y, oR, 225, 315) << polyArc(x, y, iR, 225, 315); + act = new RadioUiAction(6, QList() << Qt::Key_Left, SIMU_STR_HLP_KEY_LFT, SIMU_STR_HLP_ACT_SYS); + addRadioWidget(ui->leftbuttons->addArea(polygon, "X10/left_sys.png", act)); + + polygon.clear(); + polygon << polyArc(x, y, oR, 45, 135) << polyArc(x, y, iR, 45, 135); + act = new RadioUiAction(5, QList() << Qt::Key_Right, SIMU_STR_HLP_KEY_RGT, SIMU_STR_HLP_ACT_TELE); + addRadioWidget(ui->leftbuttons->addArea(polygon, "X10/left_tele.png", act)); + + polygon.clear(); + polygon << polyArc(x, y, oR, 135, 225) << polyArc(x, y, iR, 135, 225); + act = new RadioUiAction(4, QList() << Qt::Key_Down << Qt::Key_Delete << Qt::Key_Escape << Qt::Key_Backspace, + SIMU_STR_HLP_KEY_DN % "
" % SIMU_STR_HLP_KEYS_EXIT, SIMU_STR_HLP_ACT_RTN); + addRadioWidget(ui->leftbuttons->addArea(polygon, "X10/left_rtn.png", act)); + + act = new RadioUiAction(1, QList() << Qt::Key_PageDown, SIMU_STR_HLP_KEY_PGDN, SIMU_STR_HLP_ACT_PGDN); + addRadioWidget(ui->leftbuttons->addArea(polyArc(x, y, iR), "X10/left_page.png", act)); + + m_scrollUpAction = new RadioUiAction(-1, QList() << Qt::Key_Minus, SIMU_STR_HLP_KEY_MIN % "|" % SIMU_STR_HLP_MOUSE_UP, SIMU_STR_HLP_ACT_ROT_LFT); + m_scrollDnAction = new RadioUiAction(-1, QList() << Qt::Key_Plus << Qt::Key_Equal, SIMU_STR_HLP_KEY_PLS % "|" % SIMU_STR_HLP_MOUSE_DN, SIMU_STR_HLP_ACT_ROT_RGT); + connectScrollActions(); + + m_mouseMidClickAction = new RadioUiAction(2, QList() << Qt::Key_Enter << Qt::Key_Return, SIMU_STR_HLP_KEYS_ACTIVATE, SIMU_STR_HLP_ACT_ROT_DN); + addRadioWidget(ui->rightbuttons->addArea(polyArc(98, y, iR), "X10/right_ent.png", m_mouseMidClickAction)); + + addRadioWidget(ui->leftbuttons->addArea(QRect(10, 252, 30, 30), "X10/left_scrnsht.png", m_screenshotAction)); + + m_backlightColors << QColor(47, 123, 227); + + setLcd(ui->lcd); +} + +SimulatedUIWidgetX10::~SimulatedUIWidgetX10() +{ + delete ui; +} diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/simulation/simulateduiwidgetX10.ui opentx-companion22-2.2.1~ppa01~xenial/companion/src/simulation/simulateduiwidgetX10.ui --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/simulation/simulateduiwidgetX10.ui 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/simulation/simulateduiwidgetX10.ui 2017-11-20 18:44:06.000000000 +0000 @@ -0,0 +1,197 @@ + + + SimulatedUIWidgetX10 + + + + 0 + 0 + 825 + 292 + + + + + 0 + 0 + + + + + 825 + 292 + + + + + 825 + 292 + + + + + 0 + + + 0 + + + + + + 0 + 0 + + + + + 174 + 292 + + + + + 174 + 292 + + + + background:url(:/images/simulator/X10/right.png) + + + + + + + + 0 + 0 + + + + + 480 + 272 + + + + + 480 + 272 + + + + + 5 + + + + + + + + + 0 + 0 + + + + + 174 + 292 + + + + + 174 + 292 + + + + true + + + background:url(:/images/simulator/X10/left.png); + + + + + + + + 0 + 0 + + + + + 480 + 10 + + + + + 480 + 10 + + + + + 5 + + + + background:url(:/images/simulator/X10/top.png) + + + + + + + + 0 + 0 + + + + + 480 + 10 + + + + + 480 + 10 + + + + + 5 + false + + + + background:url(:/images/simulator/X10/bottom.png) + + + + + + + + LcdWidget + QWidget +
lcdwidget.h
+ 1 +
+ + ButtonsWidget + QWidget +
buttonswidget.h
+ 1 +
+
+ + +
diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/simulation/simulateduiwidgetX12.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/simulation/simulateduiwidgetX12.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/simulation/simulateduiwidgetX12.cpp 2017-05-14 17:18:57.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/simulation/simulateduiwidgetX12.cpp 2017-11-20 18:44:06.000000000 +0000 @@ -36,42 +36,42 @@ polygon << polyArc(x, y, oR, 225, 315) << polyArc(x, y, iR, 225, 315); act = new RadioUiAction(0, QList() << Qt::Key_PageUp, SIMU_STR_HLP_KEY_PGUP, SIMU_STR_HLP_ACT_PGUP); - addRadioWidget(ui->leftbuttons->addArea(polygon, "Horus/left_btn1.png", act)); + addRadioWidget(ui->leftbuttons->addArea(polygon, "X12/left_btn1.png", act)); polygon.clear(); polygon << polyArc(x, y, oR, 135, 225) << polyArc(x, y, iR, 135, 225); act = new RadioUiAction(1, QList() << Qt::Key_PageDown, SIMU_STR_HLP_KEY_PGDN, SIMU_STR_HLP_ACT_PGDN); - addRadioWidget(ui->leftbuttons->addArea(polygon, "Horus/left_btn2.png", act)); + addRadioWidget(ui->leftbuttons->addArea(polygon, "X12/left_btn2.png", act)); polygon.clear(); polygon << polyArc(x, y, oR, -45, 45) << polyArc(x, y, iR, -45, 45); act = new RadioUiAction(3, QList() << Qt::Key_Up, SIMU_STR_HLP_KEY_UP, SIMU_STR_HLP_ACT_MDL); - addRadioWidget(ui->rightbuttons->addArea(polygon, "Horus/right_btnU.png", act)); + addRadioWidget(ui->rightbuttons->addArea(polygon, "X12/right_btnU.png", act)); polygon.clear(); polygon << polyArc(x, y, oR, 225, 315) << polyArc(x, y, iR, 225, 315); act = new RadioUiAction(6, QList() << Qt::Key_Left, SIMU_STR_HLP_KEY_LFT, SIMU_STR_HLP_ACT_SYS); - addRadioWidget(ui->rightbuttons->addArea(polygon, "Horus/right_btnL.png", act)); + addRadioWidget(ui->rightbuttons->addArea(polygon, "X12/right_btnL.png", act)); polygon.clear(); polygon << polyArc(x, y, oR, 45, 135) << polyArc(x, y, iR, 45, 135); act = new RadioUiAction(5, QList() << Qt::Key_Right, SIMU_STR_HLP_KEY_RGT, SIMU_STR_HLP_ACT_TELE); - addRadioWidget(ui->rightbuttons->addArea(polygon, "Horus/right_btnR.png", act)); + addRadioWidget(ui->rightbuttons->addArea(polygon, "X12/right_btnR.png", act)); polygon.clear(); polygon << polyArc(x, y, oR, 135, 225) << polyArc(x, y, iR, 135, 225); act = new RadioUiAction(4, QList() << Qt::Key_Down << Qt::Key_Delete << Qt::Key_Escape << Qt::Key_Backspace, SIMU_STR_HLP_KEY_DN % "
" % SIMU_STR_HLP_KEYS_EXIT, SIMU_STR_HLP_ACT_RTN); - addRadioWidget(ui->rightbuttons->addArea(polygon, "Horus/right_btnD.png", act)); + addRadioWidget(ui->rightbuttons->addArea(polygon, "X12/right_btnD.png", act)); m_scrollUpAction = new RadioUiAction(-1, QList() << Qt::Key_Minus, SIMU_STR_HLP_KEY_MIN % "|" % SIMU_STR_HLP_MOUSE_UP, SIMU_STR_HLP_ACT_ROT_LFT); m_scrollDnAction = new RadioUiAction(-1, QList() << Qt::Key_Plus << Qt::Key_Equal, SIMU_STR_HLP_KEY_PLS % "|" % SIMU_STR_HLP_MOUSE_DN, SIMU_STR_HLP_ACT_ROT_RGT); connectScrollActions(); m_mouseMidClickAction = new RadioUiAction(2, QList() << Qt::Key_Enter << Qt::Key_Return, SIMU_STR_HLP_KEYS_ACTIVATE, SIMU_STR_HLP_ACT_ROT_DN); - addRadioWidget(ui->rightbuttons->addArea(polyArc(x, y, iR), "Horus/right_ent.png", m_mouseMidClickAction)); + addRadioWidget(ui->rightbuttons->addArea(polyArc(x, y, iR), "X12/right_ent.png", m_mouseMidClickAction)); - addRadioWidget(ui->leftbuttons->addArea(QRect(9, 259, 30, 30), "Horus/left_scrnsht.png", m_screenshotAction)); + addRadioWidget(ui->leftbuttons->addArea(QRect(9, 259, 30, 30), "X12/left_scrnsht.png", m_screenshotAction)); m_backlightColors << QColor(47, 123, 227); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/simulation/simulateduiwidgetX12.ui opentx-companion22-2.2.1~ppa01~xenial/companion/src/simulation/simulateduiwidgetX12.ui --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/simulation/simulateduiwidgetX12.ui 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/simulation/simulateduiwidgetX12.ui 2017-11-20 18:44:06.000000000 +0000 @@ -68,7 +68,7 @@ true - background:url(:/images/simulator/Horus/left.png); + background:url(:/images/simulator/X12/left.png); @@ -93,7 +93,7 @@ - background:url(:/images/simulator/Horus/led.png) + background:url(:/images/simulator/X12/led.png) @@ -123,7 +123,7 @@ - background:url(:/images/simulator/Horus/top.png) + background:url(:/images/simulator/X12/top.png) @@ -148,7 +148,7 @@ - background:url(:/images/simulator/Horus/border-right.png) + background:url(:/images/simulator/X12/border-right.png) @@ -173,7 +173,7 @@ - background:url(:/images/simulator/Horus/right.png) + background:url(:/images/simulator/X12/right.png) @@ -231,7 +231,7 @@ - background:url(:/images/simulator/Horus/bottom.png) + background:url(:/images/simulator/X12/bottom.png) diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/simulation/simulatorinterface.h opentx-companion22-2.2.1~ppa01~xenial/companion/src/simulation/simulatorinterface.h --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/simulation/simulatorinterface.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/simulation/simulatorinterface.h 2017-11-20 18:44:06.000000000 +0000 @@ -83,16 +83,20 @@ struct gVarMode_t { int16_t value; uint8_t mode; + uint8_t prec:2; + uint8_t unit:2; gVarMode_t(int i = 0) { set(i); } void set(int i) { + unit = (i >> 26) & 0x3; + prec = (i >> 24) & 0x3; mode = (i >> 16) & 0xFF; value = (i & 0xFFFF); } operator int() { - return ((mode << 16) | (value & 0xFFFF)); + return (((unit & 0x3) << 26) | ((prec & 0x3) << 24) | ((mode & 0xFF) << 16) | (value & 0xFFFF)); } gVarMode_t & operator =(const int i) { set(i); @@ -106,7 +110,7 @@ int16_t chans[CPN_MAX_CHNOUT]; // final channel outputs int16_t ex_chans[CPN_MAX_CHNOUT]; // raw mix outputs - int16_t gvars[CPN_MAX_FLIGHT_MODES][CPN_MAX_GVARS]; + qint32 gvars[CPN_MAX_FLIGHT_MODES][CPN_MAX_GVARS]; int trims[CPN_MAX_TRIMS]; // Board::TrimAxes enum bool vsw[CPN_MAX_LOGICAL_SWITCHES]; // virtual/logic switches int8_t phase; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/simulation/simulatormainwindow.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/simulation/simulatormainwindow.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/simulation/simulatormainwindow.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/simulation/simulatormainwindow.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -33,6 +33,7 @@ #endif #include +#include #include #include @@ -69,6 +70,14 @@ return; } + if (g.fwTraceLog() && !g.appLogsDir().isEmpty() && QDir().mkpath(g.appLogsDir())) { + // send firmware TRACE events to log file + QString fn = g.appLogsDir() % "/FirmwareDebug_" % QDateTime::currentDateTime().toString("yy-MM-dd_HH-mm-ss") % ".log"; + m_simuLogFile.setFileName(fn); + if (m_simuLogFile.open(QIODevice::WriteOnly | QIODevice::Text)) + m_simulator->addTracebackDevice(&m_simuLogFile); + } + m_simulator->moveToThread(&simuThread); simuThread.start(); @@ -140,8 +149,6 @@ connect(ui->actionScreenshot, &QAction::triggered, m_simulatorWidget, &SimulatorWidget::captureScreenshot); connect(m_simulatorWidget, &SimulatorWidget::windowTitleChanged, this, &SimulatorMainWindow::setWindowTitle); } - - } SimulatorMainWindow::~SimulatorMainWindow() @@ -164,6 +171,10 @@ if (m_simulator) { simuThread.quit(); simuThread.wait(); + if (m_simuLogFile.isOpen()) { + m_simulator->removeTracebackDevice(&m_simuLogFile); + m_simuLogFile.close(); + } delete m_simulator; } SimulatorLoader::unloadSimulator(m_simulatorId); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/simulation/simulatormainwindow.h opentx-companion22-2.2.1~ppa01~xenial/companion/src/simulation/simulatormainwindow.h --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/simulation/simulatormainwindow.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/simulation/simulatormainwindow.h 2017-10-31 16:16:43.000000000 +0000 @@ -24,6 +24,7 @@ #include "simulator.h" #include +#include #include #include @@ -99,6 +100,7 @@ QDockWidget * m_outputsDockWidget; QThread simuThread; + QFile m_simuLogFile; QVector m_keymapHelp; QString m_simulatorId; QString m_exitStatusMsg; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/simulation/simulatorwidget.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/simulation/simulatorwidget.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/simulation/simulatorwidget.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/simulation/simulatorwidget.cpp 2017-11-20 18:44:06.000000000 +0000 @@ -80,9 +80,11 @@ radioUiWidget = new SimulatedUIWidgetX9E(simulator, this); break; case Board::BOARD_X12S : - case Board::BOARD_X10 : radioUiWidget = new SimulatedUIWidgetX12(simulator, this); break; + case Board::BOARD_X10 : + radioUiWidget = new SimulatedUIWidgetX10(simulator, this); + break; default: radioUiWidget = new SimulatedUIWidget9X(simulator, this); break; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/simulation/telemetrysimu.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/simulation/telemetrysimu.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/simulation/telemetrysimu.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/simulation/telemetrysimu.cpp 2017-11-15 20:54:40.000000000 +0000 @@ -23,6 +23,7 @@ #include "ui_telemetrysimu.h" #include "simulatorinterface.h" #include "radio/src/telemetry/frsky.h" +#include TelemetrySimulator::TelemetrySimulator(QWidget * parent, SimulatorInterface * simulator): QWidget(parent), @@ -211,9 +212,7 @@ SET_INSTANCE(accy_inst, ACCY_FIRST_ID, 0); SET_INSTANCE(accz_inst, ACCZ_FIRST_ID, 0); - ui->rxbt_ratio->setValue(simulator->getSensorRatio(BATT_ID) / 10.0); - ui->A1_ratio->setValue(simulator->getSensorRatio(ADC1_ID) / 10.0); - ui->A2_ratio->setValue(simulator->getSensorRatio(ADC2_ID) / 10.0); + refreshSensorRatios(); } void setSportPacketCrc(uint8_t * packet) @@ -252,6 +251,13 @@ return true; } +void TelemetrySimulator::refreshSensorRatios() +{ + ui->rxbt_ratio->setValue(simulator->getSensorRatio(BATT_ID) / 10.0); + ui->A1_ratio->setValue(simulator->getSensorRatio(ADC1_ID) / 10.0); + ui->A2_ratio->setValue(simulator->getSensorRatio(ADC2_ID) / 10.0); +} + void TelemetrySimulator::generateTelemetryFrame() { static int item = 0; @@ -268,6 +274,7 @@ #if defined(XJT_VERSION_ID) generateSportPacket(buffer, 1, DATA_FRAME, XJT_VERSION_ID, 11); #endif + refreshSensorRatios(); // placed here in order to call this less often break; case 1: @@ -621,6 +628,7 @@ { TelemetrySimulator::LogPlaybackController::ui = ui; stepping = false; + logFileGpsCordsInDecimalFormat = false; // initialize the map - TODO: how should this be localized? colToFuncMap.clear(); colToFuncMap.insert("RxBt(V)", RXBT_V); @@ -686,6 +694,31 @@ return QDateTime::fromString(datePart + " " + timePart, format); } +void TelemetrySimulator::LogPlaybackController::checkGpsFormat() +{ + // sample the first record to check if cords are in decimal format + logFileGpsCordsInDecimalFormat = false; + if(csvRecords.count() > 1) { + QStringList keys = csvRecords[0].split(','); + if(keys.contains("GPS")) { + int gpsColIndex = keys.indexOf("GPS"); + QStringList firstRowVlues = csvRecords[1].split(','); + QString gpsSample = firstRowVlues[gpsColIndex]; + QStringList cords = gpsSample.simplified().split(' '); + if (cords.count() == 2) { + // frsky and TBS crossfire GPS sensor logs cords in decimal format with a precision of 6 places + // if this format is met there is no need to call convertDegMin later on when processing the file + QRegularExpression decimalCoordinateFormatRegex("^[-+]?\\d{1,2}[.]\\d{6}$"); + QRegularExpressionMatch latFormatMatch = decimalCoordinateFormatRegex.match(cords[0]); + QRegularExpressionMatch lonFormatMatch = decimalCoordinateFormatRegex.match(cords[1]); + if (lonFormatMatch.hasMatch() && latFormatMatch.hasMatch()) { + logFileGpsCordsInDecimalFormat = true; + } + } + } + } +} + void TelemetrySimulator::LogPlaybackController::calcLogFrequency() { // examine up to 20 rows to determine log frequency in seconds @@ -754,6 +787,7 @@ supportedCols.clear(); recordIndex = 1; calcLogFrequency(); + checkGpsFormat(); } ui->logFileLabel->setText(QFileInfo(logFileNameAndPath).fileName()); // iterate through all known mappings and add those that are used @@ -862,8 +896,15 @@ if (lonLat.count() < 2) { return ""; // invalid format } - double lon = convertDegMin(lonLat[0]); - double lat = convertDegMin(lonLat[1]); + double lon, lat; + if (logFileGpsCordsInDecimalFormat) { + lat = lonLat[0].toDouble(); + lon = lonLat[1].toDouble(); + } + else { + lon = convertDegMin(lonLat[0]); + lat = convertDegMin(lonLat[1]); + } return QString::number(lat) + ", " + QString::number(lon); } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/simulation/telemetrysimu.h opentx-companion22-2.2.1~ppa01~xenial/companion/src/simulation/telemetrysimu.h --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/simulation/telemetrysimu.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/simulation/telemetrysimu.h 2017-11-15 20:54:40.000000000 +0000 @@ -67,6 +67,7 @@ void onStop(); void onPositionIndicatorChanged(int value); void onReplayRateChanged(int value); + void refreshSensorRatios(); void generateTelemetryFrame(); protected: @@ -95,6 +96,7 @@ void updatePositionLabel(int32_t percentage); void setUiDataValues(); double logFrequency; // in seconds + bool logFileGpsCordsInDecimalFormat; private: enum CONVERT_TYPE { @@ -148,6 +150,7 @@ double convertDegMin(QString input); QDateTime parseTransmittterTimestamp(QString row); void calcLogFrequency(); + void checkGpsFormat(); QMap colToFuncMap; // contains all 'known' column headings and how they are to be processed Ui::TelemetrySimulator * ui; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/simulator.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/simulator.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/simulator.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/simulator.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -19,6 +19,7 @@ */ #include +#include #include #include #include @@ -42,6 +43,7 @@ using namespace Simulator; +QFile simuDbgLog; int finish(int exitCode); void showMessage(const QString & message, enum QMessageBox::Icon icon = QMessageBox::NoIcon, bool useConsole = false) @@ -56,10 +58,9 @@ } // use GUI QMessageBox msgBox; - QString escMsg(message); - escMsg.replace("<", "<"); - msgBox.setText("
" + escMsg + "
"); + msgBox.setText("
" + message.toHtmlEscaped() + "
"); msgBox.setIcon(icon); + msgBox.setWindowTitle(QApplication::translate("SimulatorMain", "OpenTx Simulator")); msgBox.exec(); } @@ -251,6 +252,14 @@ g.init(); // init settings before installing translations + if (AppDebugMessageHandler::instance() && g.appDebugLog() && !g.appLogsDir().isEmpty() && QDir().mkpath(g.appLogsDir())) { + QString fn = g.appLogsDir() % "/SimulatorDebug_" % QDateTime::currentDateTime().toString("yy-MM-dd_HH-mm-ss") % ".log"; + simuDbgLog.setFileName(fn); + if (simuDbgLog.open(QIODevice::WriteOnly | QIODevice::Text)) { + AppDebugMessageHandler::instance()->addOutputDevice(&simuDbgLog); + } + } + Translations::installTranslators(); #if defined(JOYSTICKS) || defined(SIMU_AUDIO) @@ -365,5 +374,9 @@ #endif qDebug() << "SIMULATOR EXIT" << exitCode; + if (simuDbgLog.isOpen()) { + AppDebugMessageHandler::instance()->removeOutputDevice(&simuDbgLog); + simuDbgLog.close(); + } return exitCode; } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/storage/appdata.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/storage/appdata.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/storage/appdata.cpp 2017-05-31 19:49:19.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/storage/appdata.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -460,16 +460,6 @@ QString AppData::snapshotDir() { return _snapshotDir; } QString AppData::updatesDir() { return _updatesDir; } -bool AppData::jsSupport() { return _jsSupport; } -bool AppData::maximized() { return _maximized; } -bool AppData::showSplash() { return _showSplash; } -bool AppData::snapToClpbrd() { return _snapToClpbrd; } -bool AppData::autoCheckApp() { return _autoCheckApp; } -bool AppData::autoCheckFw() { return _autoCheckFw; } -bool AppData::simuSW() { return _simuSW; } -bool AppData::tabbedMdi() { return _tabbedMdi; } -bool AppData::removeModelSlots() { return _remvModelSlots; } - int AppData::newModelAction() { return _newModelAction; } int AppData::backLight() { return _backLight; } int AppData::embedSplashes() { return _embedSplashes; } @@ -517,16 +507,6 @@ void AppData::snapshotDir (const QString x) { store(x, _snapshotDir, "snapshotpath" );} void AppData::updatesDir (const QString x) { store(x, _updatesDir, "lastUpdatesDir" );} -void AppData::maximized (const bool x) { store(x, _maximized, "maximized" );} -void AppData::jsSupport (const bool x) { store(x, _jsSupport, "js_support" );} -void AppData::showSplash (const bool x) { store(x, _showSplash, "show_splash" );} -void AppData::snapToClpbrd (const bool x) { store(x, _snapToClpbrd, "snapshot_to_clipboard" );} -void AppData::autoCheckApp (const bool x) { store(x, _autoCheckApp, "startup_check_companion" );} -void AppData::autoCheckFw (const bool x) { store(x, _autoCheckFw, "startup_check_fw" );} -void AppData::simuSW (const bool x) { store(x, _simuSW, "simuSW" );} -void AppData::tabbedMdi (const bool x) { store(x, _tabbedMdi, "tabbedMdi" );} -void AppData::removeModelSlots(const bool x) { store(x, _remvModelSlots, "removeModelSlots" );} - void AppData::newModelAction (const int x) { store(x, _newModelAction, "newModelAction" );} void AppData::backLight (const int x) { store(x, _backLight, "backLight" );} void AppData::embedSplashes (const int x) { store(x, _embedSplashes, "embedded_splashes" );} @@ -558,12 +538,10 @@ qRegisterMetaTypeStreamOperators("SimulatorOptions"); firstUse = false; - upgradeFromVersion = ""; QSettings settings(COMPANY, PRODUCT); if (!settings.contains("settings_version")) { - if (!importSettings(settings)) - firstUse = true; + firstUse = true; } convertSettings(settings); @@ -611,23 +589,24 @@ getset( _snapshotDir, "snapshotpath" ,"" ); getset( _updatesDir, "lastUpdatesDir" ,"" ); - getset( _enableBackup, "enableBackup" ,false ); - getset( _backupOnFlash, "backupOnFlash" ,true ); - - getset( _outputDisplayDetails, "outputDisplayDetails" ,false ); - getset( _checkHardwareCompatibility, "checkHardwareCompatibility" ,true ); - getset( _useCompanionNightlyBuilds, "useCompanionNightlyBuilds" ,false ); - getset( _useFirmwareNightlyBuilds, "useFirmwareNightlyBuilds" ,false ); - - getset( _jsSupport, "js_support" ,false ); - getset( _maximized, "maximized" ,false ); - getset( _showSplash, "show_splash" ,true ); - getset( _snapToClpbrd, "snapshot_to_clipboard" ,false ); - getset( _autoCheckApp, "startup_check_companion" ,true ); - getset( _autoCheckFw, "startup_check_fw" ,true ); - getset( _simuSW, "simuSW" ,false ); - getset( _tabbedMdi, "tabbedMdi" ,false ); - getset( _remvModelSlots, "removeModelSlots" ,true ); + getset( _OpenTxBranch, "OpenTxBranch", BRANCH_RELEASE_STABLE); + + appLogsDir_init(); + enableBackup_init(); + backupOnFlash_init(); + outputDisplayDetails_init(); + checkHardwareCompatibility_init(); + removeModelSlots_init(); + maximized_init(); + simuSW_init(); + tabbedMdi_init(); + appDebugLog_init(); + fwTraceLog_init(); + jsSupport_init(); + showSplash_init(); + snapToClpbrd_init(); + autoCheckApp_init(); + autoCheckFw_init(); getset( _newModelAction, "newModelAction" ,1 ); getset( _backLight, "backLight" ,0 ); @@ -670,55 +649,85 @@ } } -bool AppData::importSettings(QSettings & toSettings) +bool AppData::hasCurrentSettings() +{ + QSettings settings(COMPANY, PRODUCT); + if (!settings.contains("settings_version")) { + return false; + } + return true; +} + +bool AppData::findPreviousVersionSettings(QString * version) { QSettings * fromSettings = NULL; + *version = ""; QSettings settings21("OpenTX", "Companion 2.1"); if (settings21.contains("settings_version")) { fromSettings = &settings21; - upgradeFromVersion = "2.1"; + *version = "2.1"; } else { settings21.clear(); } - if (!fromSettings) { - QSettings settings20("OpenTX", "Companion 2.0"); - if (settings20.contains("settings_version")) { + QSettings settings20("OpenTX", "Companion 2.0"); + if (settings20.contains("settings_version")) { + if (!fromSettings) { fromSettings = &settings20; - upgradeFromVersion = "2.0"; - } - else { - settings20.clear(); + *version = "2.0"; } } + else { + settings20.clear(); + } - if (!fromSettings) { - QSettings settings16("OpenTX", "OpenTX Companion"); - if (settings16.contains("settings_version")) { + QSettings settings16("OpenTX", "OpenTX Companion"); + if (settings16.contains("settings_version")) { + if (!fromSettings) { fromSettings = &settings16; - upgradeFromVersion = "1.x"; - } - else { - settings16.clear(); + *version = "1.x"; } } - - if (!fromSettings) { - QSettings settings9x("companion9x", "companion9x"); - if (settings9x.contains("default_mode")) { - fromSettings = &settings9x; - upgradeFromVersion = "Companion9X"; - } - else { - settings9x.clear(); - } + else { + settings16.clear(); } if (!fromSettings) return false; + return true; +} + +bool AppData::importSettings(QString fromVersion) +{ + QSettings toSettings(COMPANY, PRODUCT); + + QString fromCompany; + QString fromProduct; + + upgradeFromVersion = ""; + + if (fromVersion == "2.1") { + fromCompany = "OpenTX"; + fromProduct = "Companion 2.1"; + } + else if (fromVersion == "2.0") { + fromCompany = "OpenTX"; + fromProduct = "Companion 2.0"; + } + else if (fromVersion == "1.x") { + fromCompany = "OpenTX"; + fromProduct = "OpenTX Companion"; + } + else + return false; + + upgradeFromVersion = fromVersion; + + QSettings fromSettings(fromCompany, fromProduct); + // do not copy these settings QStringList excludeKeys = QStringList() << "compilation-server"; #ifdef WIN32 @@ -729,59 +738,11 @@ #endif // import settings - foreach (const QString & key, fromSettings->allKeys()) { - if (fromSettings->value(key).isValid() && !excludeKeys.contains(key)) { - toSettings.setValue(key, fromSettings->value(key)); + foreach (const QString & key, fromSettings.allKeys()) { + if (fromSettings.value(key).isValid() && !excludeKeys.contains(key)) { + toSettings.setValue(key, fromSettings.value(key)); } } - // Additional adjustments for companion9x settings - if (fromSettings->applicationName() == "companion9x") { - // Store old values in new locations - autoCheckApp(toSettings.value("startup_check_companion9x", true).toBool()); - toSettings.setValue("useWizard", toSettings.value("wizardEnable", true)); - - // Convert and store the firmware type - QString fwType = toSettings.value("firmware", "").toString(); - fwType.replace("open9x", "opentx"); - fwType.replace("x9da", "x9d"); - - profile[0].init( 0 ); - profile[0].fwType( fwType ); - // Move the Companion9x profile settings to profile0, the new default profile - profile[0].name( toSettings.value( "Name", "My Radio").toString()); - profile[0].sdPath( toSettings.value( "sdPath", "" ).toString()); - profile[0].splashFile( toSettings.value( "SplashFileName", "" ).toString()); - profile[0].burnFirmware( toSettings.value( "burnFirmware", false ).toBool()); - profile[0].renameFwFiles( toSettings.value( "rename_firmware_files", false ).toBool()); - profile[0].channelOrder( toSettings.value( "default_channel_order", "0" ).toInt()); - profile[0].defaultMode( toSettings.value( "default_mode", "1" ).toInt()); - - // Ensure that the default profile has a name - if ( profile[0].name().isEmpty() ) - profile[0].name("My Radio"); - - // Delete obsolete settings fields from companion9x - toSettings.remove("ActiveProfile"); - toSettings.remove("burnFirmware"); - toSettings.remove("custom_id"); - toSettings.remove("default_channel_order"); - toSettings.remove("default_mode"); - toSettings.remove("firmware"); - toSettings.remove("lastFw"); - toSettings.remove("modelEditTab"); - toSettings.remove("Name"); - toSettings.remove("patchImage"); - toSettings.remove("rename_firmware_files"); - toSettings.remove("sdPath"); - toSettings.remove("SplashFileName"); - toSettings.remove("startup_check_companion9x"); - toSettings.remove("warningId"); - toSettings.remove("wizardEnable"); - - // Select the new default profile as current profile - id( 0 ); - } - return true; } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/storage/appdata.h opentx-companion22-2.2.1~ppa01~xenial/companion/src/storage/appdata.h --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/storage/appdata.h 2017-05-31 19:49:19.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/storage/appdata.h 2017-12-17 16:22:27.000000000 +0000 @@ -25,11 +25,14 @@ #ifndef _APPDATA_H_ #define _APPDATA_H_ + #include #include #include #include +#include +#include "constants.h" #include "simulator.h" #define COMPANY "OpenTX" @@ -226,21 +229,37 @@ QString groupId(); }; -#define BOOL_PROPERTY(name, dflt) \ + +#define PROPERTY4(type, name, key, dflt) \ public: \ - inline bool name() { return _ ## name; } \ - void name(const bool val) { store(val, _ ## name, # name); } \ + inline type name() { return _ ## name; } \ + void name(const type val) { store(val, _ ## name, # key); } \ private: \ - bool _ ## name; + void name ## _init() { getset(_ ## name, # key, dflt); } \ + type _ ## name; + +#define PROPERTY(type, name, dflt) PROPERTY4(type, name, name, dflt) class AppData: protected CompStoreObj { - BOOL_PROPERTY(enableBackup, false) - BOOL_PROPERTY(backupOnFlash, true) - BOOL_PROPERTY(outputDisplayDetails, false) - BOOL_PROPERTY(checkHardwareCompatibility, true) - BOOL_PROPERTY(useCompanionNightlyBuilds, false) - BOOL_PROPERTY(useFirmwareNightlyBuilds, false) + PROPERTY(bool, enableBackup, false) + PROPERTY(bool, backupOnFlash, true) + PROPERTY(bool, outputDisplayDetails, false) + PROPERTY(bool, checkHardwareCompatibility, true) + PROPERTY(bool, removeModelSlots, true) + PROPERTY(bool, maximized, false) + PROPERTY(bool, simuSW, false) + PROPERTY(bool, tabbedMdi, false) + PROPERTY(bool, appDebugLog, false) + PROPERTY(bool, fwTraceLog, false) + + PROPERTY(unsigned, OpenTxBranch, BRANCH_RELEASE_STABLE); + + PROPERTY4(bool, jsSupport, js_support ,false) + PROPERTY4(bool, showSplash, show_splash ,true) + PROPERTY4(bool, snapToClpbrd, snapshot_to_clipboard ,false) + PROPERTY4(bool, autoCheckApp, startup_check_companion ,true) + PROPERTY4(bool, autoCheckFw, startup_check_fw ,true) // All the global variables public: @@ -280,16 +299,7 @@ QString _libDir; QString _snapshotDir; QString _updatesDir; - - bool _maximized; - bool _jsSupport; - bool _showSplash; - bool _snapToClpbrd; - bool _autoCheckApp; - bool _autoCheckFw; - bool _simuSW; - bool _tabbedMdi; - bool _remvModelSlots; + PROPERTY(QString, appLogsDir, QString(QStandardPaths::writableLocation(QStandardPaths::DocumentsLocation) % "/" COMPANY "/DebugLogs")) int _newModelAction; // 0=no action; 1=model wizard; 2=model edit int _backLight; @@ -341,16 +351,6 @@ QString snapshotDir(); QString updatesDir(); - bool jsSupport(); - bool maximized(); - bool showSplash(); - bool snapToClpbrd(); - bool autoCheckApp(); - bool autoCheckFw(); - bool simuSW(); - bool tabbedMdi(); - bool removeModelSlots(); - int newModelAction(); int backLight(); int embedSplashes(); @@ -399,16 +399,6 @@ void snapshotDir (const QString); void updatesDir (const QString); - void maximized (const bool); - void jsSupport (const bool); - void showSplash (const bool); - void snapToClpbrd (const bool); - void autoCheckApp (const bool); - void autoCheckFw (const bool); - void simuSW (const bool); - void tabbedMdi (const bool); - void removeModelSlots(const bool); - void newModelAction (const int); void backLight (const int); void embedSplashes (const int); @@ -431,10 +421,20 @@ QMap getActiveProfiles(); inline bool isFirstUse() const { return firstUse; } inline QString previousVersion() const { return upgradeFromVersion; } + bool hasCurrentSettings(); + bool findPreviousVersionSettings(QString * version); + bool importSettings(QString fromVersion); + + inline DownloadBranchType boundedOpenTxBranch() { +#if defined(ALLOW_NIGHTLY_BUILDS) + return qBound(BRANCH_RELEASE_STABLE, DownloadBranchType(OpenTxBranch()), BRANCH_NIGHTLY_UNSTABLE); +#else + return qBound(BRANCH_RELEASE_STABLE, DownloadBranchType(OpenTxBranch()), BRANCH_RC_TESTING); +#endif + } protected: void convertSettings(QSettings & settings); - bool importSettings(QSettings & toSettings); bool firstUse; QString upgradeFromVersion; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/storage/storage.h opentx-companion22-2.2.1~ppa01~xenial/companion/src/storage/storage.h --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/storage/storage.h 2017-04-27 08:57:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/storage/storage.h 2017-12-17 16:22:27.000000000 +0000 @@ -71,8 +71,9 @@ { switch (board) { case Board::BOARD_X12S: - case Board::BOARD_X10: return 0x3478746F; + case Board::BOARD_X10: + return 0x3778746F; case Board::BOARD_TARANIS_X7: return 0x3678746F; case Board::BOARD_TARANIS_X9E: @@ -82,6 +83,7 @@ return 0x3378746F; case Board::BOARD_SKY9X: case Board::BOARD_AR9X: + case Board::BOARD_9XRPRO: return 0x3278746F; case Board::BOARD_MEGA2560: case Board::BOARD_GRUVIN9X: diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/translations/companion_fr.ts opentx-companion22-2.2.1~ppa01~xenial/companion/src/translations/companion_fr.ts --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/translations/companion_fr.ts 2017-05-31 19:49:19.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/translations/companion_fr.ts 2017-12-17 16:22:27.000000000 +0000 @@ -11,7 +11,7 @@ Yes, controlled by a single channel - Oui, contrôlés par une 1 voie + @@ -65,37 +65,37 @@ Éditer les réglages - + Radio Profile Profil de radio - + Default Channel Order Ordre des voies par défaut - + Build Options Options de compilation - + Menu Language Langue des menus - + Default Stick Mode Mode par défaut - + Select Image Sélectionner une image - + Mode selection: Mode 1: @@ -136,477 +136,536 @@ - + Mode 1 (RUD ELE THR AIL) Mode 1 (DIR PROF GAZ AIL) - + Mode 2 (RUD THR ELE AIL) Mode 2 (DIR GAZ PROF AIL) - + Mode 3 (AIL ELE THR RUD) Mode 3 (AIL PROF GAZ DIR) - + Mode 4 (AIL THR ELE RUD) Mode 4 (AIL GAZ PROF DIR) - + Splash Screen Ecran d'accueil - - + + The profile specific folder, if set, will override general Backup folder Dossier de sauvegarde spécifique au profil courant, si défini remplace le réglage de l'application - + Backup folder Dossier de sauvegarde - + If set it will override the application general setting Si défini, remplace le réglage de l'application pour ce profil - + if set, will override general backup enable Si défini, remplace le réglage de l'application pour ce profil - + <html><head/><body><p>Channel order</p><p><br/></p><p>Defines the order of the default mixes created on a new model.</p></body></html> <html><head/><body><p>Ordre des voies</p><p><br/></p><p>Détermine l'ordre des mixages par défaut sur un nouveau modèle.</p></body></html> - + R E T A D P G A - + R E A T D P A G - + R T E A D G P A - + R T A E D G A P - + R A E T D A P G - + R A T E D A G P - + E R T A P D G A - + E R A T P D A G - + E T R A P G D A - + E T A R P G A D - + E A R T P A D G - + E A T R P A G D - + T R E A G D P A - + T R A E G D A P - + T E R A G P D A - + T E A R G P A D - + T A R E G A D P - + T A E R G A P D - + A R E T A D P G - + A R T E A D G P - + A E R T A P D G - + A E T R A P G D - + A T R E A G D P - + A T E R A G P D - - - - - + + + + + + Select Folder Sélectionner dossier - + Select Executable Sélectionner exécutable - - Use OpenTX firmware nightly builds - Utlilser les nightly builds du firmware - - - - Use Companion nightly builds - Utlilser les nightly builds de Companion - - - + Simulator Volume Gain Gain de volume du simulateur - + Profile Name Nom du profil - + Clear Image Effacer l'image - + Append version number to FW file name Ajouter le numéro de version au nom du fichier téléchargé - + Offer to write FW to Tx after download Proposer de transférer le firmware à la radio après téléchargement - + Radio Type Type de radio - + Other Settings Autres réglages - + General Settings Paramètres généraux - + SD Structure path Chemin de la structure de la carte SD - + Set voice language. May be different from firmware language Langue des voix. Peut être différente de la langue du firmware - + Voice Language Langue des voix - + Application Settings Réglages de l'application - + Show splash screen when Companion starts Afficher l'écran d'accueil au lancement de Companion - + Automatic check for Companion updates Vérifier la présence de mises à jour de Companion automatiquement - - + + Enable automatic backup before writing firmware Sauvegarder les réglages et modèles automatiquement lors des transferts - + Automatic check for OpenTX firmware updates Vérifier la présence de mises à jour de firmware automatiquement - + Splash Screen Library Bibliothèque d'écrans d'accueil - - Files to keep - Fichiers à conserver - - - + Google Earth Executable Exécutable Google Earth - + Only show user splash images Ne montrer que les images de l'utilisateur - + Show user and companion splash images Montrer les images de Companion et de l'utilisateur - + User Splash Screens Ecrans d'accueil personnalisés - + Automatic Backup Folder Dossier de sauvegardes automatiques - + Simulator Settings Paramètres du simulateur - + Simulator BackLight Rétroéclairage du simulateur - + Enable Actif - + Action on New Model Action par défaut "Ajout Modèle" - + Use model wizard Assistant - + Open model editor Éditer modèle - + Just create the model Créer modèle - + <html><head/><body><p>This option maintains the behaviour from older OpenTx versions where empty model slots are preserved when a model is deleted or moved. </p><p>When this option is de-selected, the other models may be re-arranged to fill the gap left by the removed model.</p></body></html> <html><head/><body><p><b><u>/!\</u> Uniquement pour les radios sans catégories <u>/!\</u></b></p><p>Cette option maintient le comportement des anciennes versions d’OpenTx où les emplacements des modèles vides sont conservés lorsqu'un modèle est supprimé ou déplacé.</p><p>Lorsque cette option est désélectionnée, les autres modèles peuvent être réarrangés pour combler l'écart laissé par le modèle supprimé.</p></body></html> - + + Use releases (stable) + Utiliser version officielle (stable) + + + + Use releases and release candidates (testing) + Utiliser version officielle et candidate (test) + + + + Use nightly builds (unstable) + Utiliser version "nightly builds" (unstable) + + + + most recently used files + fichiers récemment utilisés + + + + Startup Settings + Paramètres de démarrage + + + + Remember + Mémoriser + + + + Output Logs Folder + Répertoire des logs sauvegardés + + + Remove empty model slots when deleting models (only applies for radios w/out categories) Supprimer les emplacements vides lors de la suppression de modèles - + + Debug Output Logging + Log les messages de debug + + + + <html><head/><body><p>Keep a log of all debugging messages generated by the desktop Companion/Simulator applications. An OpenTX developer may request this to help diagnose an issue.</p></body></html> + <html><head/><body><p>Garder un log de tous les messages de débogage générés par les applications Companion/Simulateur. Un développeur OpenTX peut demander ce log afin d'aider à diagnostiquer un problème.</p></body></html> + + + + Application (Companion/Simulator) + Application (Companion/Simulateur) + + + + <html><head/><body><p>Keep a log of all messages generated by the radio firmware when running in Simulator. This is the same information one would also see in the Simulator <span style=" font-style:italic;">Debug Output</span> window.</p></body></html> + <html><head/><body><p>Conserver un log de tous les messages générés par le firmware radio lors de l'exécution du Simulateur. C'est la même information visible depuis le Simulateur dans la <span style=" font-style:italic;">Fenêtre de débogage</span>.</p></body></html> + + + + Radio Firmware (in Simulator) + Firmware radio (Simulateur) + + + Blue Bleu - + Green Vert - + Red Rouge - + Orange Orange - + Yellow Jaune - + + Screenshot capture folder + Répertoire des captures d'écran + + + Joystick - + Calibrate Calibrer - - Simulator capture folder - Dossier des captures d'écran - - - + Only capture to clipboard Capturer dans le presse-papiers uniquement - + Remember simulator switch values Mémoriser les positions des inters du simulateur - + My Radio Ma radio - + Select your snapshot folder Sélectionner le dossier où stocker les captures d'écran - - + + No joysticks found Aucun Joystick trouvé - + EMPTY: No radio settings stored in profile VIDE: Aucune donnée stockée dans le profil - + AVAILABLE: Radio settings of unknown age DISPONIBLE: Réglages enregistrés à une date inconnue - + AVAILABLE: Radio settings stored %1 DISPONIBLE: Réglages enregistrés le %1 - + Select your library folder Sélectionner le dossier de bibliothèque - - + + Select your Models and Settings backup folder Sélectionner le dossier dans lequel une sauvegarde des réglages et modèles sera placée automatiquement lors de chaque opération - + + Select a folder for application logs + Sélectionner un dossier pour le log des applications + + + Select Google Earth executable Sélectionner l'emplacement de l'exécutable Google Earth - + Select the folder replicating your SD structure Sélectionner un dossier contenant une copie des dossiers de la carte SD - + Open Image to load Ouvrir l'image à charger - + Images (%1) Images (%1) + Channel + + + CH + VOIE + + + Channels @@ -665,6 +724,93 @@ + ChecklistDialog + + + Edit Checklist + Éditer Checklist + + + + &Import... + &Importer... + + + + &Cancel + &Annuler + + + + &OK + + + + + Please note, the maximum width displayable is radio model limited. Also, renaming the model will break the link to this checklist file. + Veuillez noter que la largeur maximale affichable est limitée suivant le modèle de radio. Notez aussi que renommer le modèle va casser le lien vers ce fichier "Checklist". + + + + File: unknown + Fichier: inconnu + + + + Open Checklist + Ouvrir Checklist + + + + Checklist Files (*.txt) + Fichier Checklist (*.txt) + + + + + + + + Model Checklist + Modèle Checklist + + + + Cannot open file for writing %1: +%2. + Impossible d'ouvrir le fichier en écriture %1: +%2. + + + + Cannot write to file %1: +%2. + Impossible d'écrire dans le fichier %1: +%2. + + + + Cannot write file %1: +%2. + Impossible d'écrire le fichier %1: +%2. + + + + Cannot open file %1: +%2. + Impossible d'ouvrir le fichier %1: +%2. + + + + Cannot read file %1: +%2. + Impossible de lire le fichier %1: +%2. + + + Companion @@ -817,11 +963,11 @@ - CurveData + Curve - - CV%1 - CB%1 + + CV + CB @@ -931,72 +1077,72 @@ Nom de la courbe - + Curve %1 Courbe %1 - + %1 points - + Linear Linéaire - + Single Expo Expo simple - + Symmetrical f(x)=-f(-x) Symétrique f(x)=-f(-x) - + Symmetrical f(x)=f(-x) Symétrique f(x)=f(-x) - + Copy Copier - + Paste Coller - + Clear Effacer - + Clear all curves Effacer toutes les courbes - + Are you sure you want to reset curve %1? Etes-vous sûr de vouloir effacer la courbe %1 ? - + Are you sure you want to reset all curves? Etes-vous sûr de vouloir effacer toutes les courbes ? - + Editing curve %1 Édition de la courbe %1 - + Not enough free points in EEPROM to store the curve. Pas assez de points disponibles en mémoire pour enregistrer la courbe. @@ -1049,45 +1195,25 @@ Impossible de trouver le fichier son %1 ! - + &Delete &Supprimer - - Delete - Supprimer - - - + &Copy &Copier - - Ctrl+C - - - - + &Cut &Couper - - Ctrl+X - - - - + &Paste &Coller - - - Ctrl+V - - CustomizeSplashDialog @@ -1312,12 +1438,12 @@ Basculer le filtre on/off. - + <html><head><style>kbd {background-color: palette(alternate-base); font-size: large; white-space: nowrap;}</style></head><body><p>The filter supports two syntax types: basic matching with common wildcards as well as full Perl-style (<code>pcre</code>) Regular Expressions.</p><p>By default a filter will only show lines which match (<b>inclusive</b>). To make an <b>exclusive</b> filter which removes matching lines, prefix the filter expression with a <kbd>!</kbd> (exclamation mark).</p><p>To use <b>Regular Expressions</b> (RegEx), prefix the filter text with a <kbd>/</kbd> (slash) or <kbd>^</kbd> (up caret). <ul><li>Put the <kbd>/</kbd> or <kbd>^</kbd> after the exclusive <kbd>!</kbd> indicator if you're using one.</li><li>By default the match is case-sensitive. To make it insensitive, add the typical <kbd>/i</kbd> (slash i) operator at the end of your RegEx.</li><li>If you use a caret (^) to denote a RegEx, it will become part of the Reg. Ex. (that is, matches from start of line).</li><li>If the RegEx is invalid, the filter edit field should show a red border and you will not be able to enable the filter.</li><li>A useful resource for testing REs (with a full reference) can be found at <a href="http://www.regexr.com/">http://www.regexr.com/</a></li></ul></p><p>To use <b>basic matching</b> just type any text.<ul><li>Wildcards: <kbd>*</kbd> (asterisk) matches zero or more of any character(s), and <kbd>?</kbd> (question mark) matches any single character.</li><li>The match is always case-insensitive.</li><li>The match always starts from the beginning of a log line. To ignore characters at the start, use a leading <kbd>*</kbd> wildcard.</li><li>A trailing <kbd>*</kbd> is always implied (that is, matches anything to the end of the log line). To avoid this, use a RegEx.</li><li>You can match literal wildcard characters by prefixing them with a <kbd>\</kbd> (backslash) character (eg. "foo\*bar" matches "foo*bar").</li></ul></p><p>After <b>editing text</b>, press ENTER or TAB key (or click anywhere outside the box) to update the filter.</p><p>To <b>remove an entry</b> from the filter selector list, first choose it, and while in the line editor press <kbd>Shift-Delete</kbd> (or <kbd>Shift-Backspace</kbd>) key combination. The default filters cannot be removed. Up to 50 filters are stored.</p></body></html> <html><head><style>kbd {background-color: palette(alternate-base); font-size: large; white-space: nowrap;}</style></head><body><p>Le filtre supporte deux types de syntaxes: la recherche simple utilisant les métacaractères ou la recherche avancée utilisant les expressions régulières (<code>RegEx</code>) de type Perl.</p><p>Par défaut, un filtre ne montre que les lignes qui correspondent (<b>inclusif</b>). Pour faire un filtre <b>exclusif</b> qui supprime les lignes de correspondance, préfixez l'expression du filtre avec un <kbd>!</kbd> (point d'exclamation).</p><p>Pour utiliser les <b>Expressions Régulières</b> (RegEx), préfixez le texte du filtre avec un <kbd>/</kbd> (slash) ou <kbd>^</kbd> (accent circonflexe).<ul><li>Il faut mettre le <kbd>!</kbd> <u>avant</u> le <kbd>/</kbd> ou <kbd>^</kbd> dans le cas d'un filtre exclusif.</li><li>Par défaut, la correspondance est sensible à la casse (ex: a &ne; A). Pour la rendre insensible (ex: a = A), ajoutez l'opérateur typique <kbd>/i</kbd> (slash i) à la fin de votre RegEx.</li><li>Si vous utilisez un <kbd>^</kbd> pour désigner une RegEx, il deviendra une partie de la RegEx (<kbd>^</kbd> est le caractère de début de chaîne).</li><li>Si la RegEx n'est pas valide, le champ d'édition du filtre affichera une bordure rouge et vous ne pourrez pas activer le filtre.</li><li>Une ressource utile pour tester les RegExs (avec une référence complète) peut être trouvée sur le site <a href="http://www.regexr.com/">http://www.regexr.com/</a> (tutoriel en français: <a href="http://perl.mines-albi.fr/DocFr/perlretut.html">Expressions rationnelles/régulières en Perl</a>)</li></ul></p><p>Pour utiliser la <b>recherche simple</b>, tapez simplement le texte recherché.<ul><li>Métacaractères: le quantificateur <kbd>*</kbd> (astérisque) correspond à zéro ou plus de n'importe quel caractère, et le quantificateur <kbd>?</kbd> (point d'interrogation) correspond à un caractère unique.</li><li>La correspondance est toujours sensible à la casse.</li><li>La correspondance commence toujours au début du Log. Pour ignorer les caractères au début, utilisez le métacaractère <kbd>*</kbd>.</li><li>Un métacaractère <kbd>*</kbd> est implicitement ajouté à la fin (ainsi, toutes les correspondances valides soient bien affichées jusqu'à la fin du Log). Si vous voulez éviter ce métacaractère implicite, il faut utiliser une RegEx.</li><li>Pour rechercher un caractère qui est lui-même un métacaractère, il faut préfixer avec un <kbd>\</kbd> (backslash) (ex: "<i>toto\*titi</i>" correspond à "<i>toto*titi</i>").</li></ul></p><p>Quand l'<b>édition</b> est terminée, appuyez sur la touche ENTRER ou TAB (ou cliquez n'importe où à l'extérieur du champ du filtre) afin de mettre à jour le filtre.</p><p>Pour <b>retirer un filtre de l'historique</b>, sélectionnez-le d'abord, puis faite le raccourci clavier <kbd>Shift-Suppr</kbd> (ou <kbd>Shift-Retour Arrière</kbd>). Les filtres par défaut ne peuvent pas être effacés. Jusqu'à 50 filtres peuvent être mémorisés.</p></body></html> - + Debug Console Filter Help Aide sur les filtres pour la console de débogage @@ -1325,78 +1451,78 @@ EepromInterface - + Possible causes for this: Causes possibles: - + - Eeprom is from a newer version of OpenTX - L'EEPROM peut avoir été créée avec une version d'OpenTX plus récente - + - Eeprom is not from OpenTX - L'EEPROM peut avoir été créée avec un firmware autre qu'OpenTX - + - Eeprom is not from Th9X - L'EEPROM n'est pas une EEPROM TX9X - + - Eeprom is not from Gruvin9X - L'EEPROM n'est pas une EEPROM Gruvin9X - + - Eeprom is not from ErSky9X - L'EEPROM n'est pas une EEPROM ErSky9X - + - Eeprom is not from Er9X - L'EEPROM n'est pas une EEPROM ER9X - + - Eeprom size is invalid - La taille de l'EEPROM est invalide - + - Eeprom file system is invalid - Le système de fichier de l'EEPROM est invalide - + - Eeprom is from a unknown board - L'EEPROM ne correspond à aucune carte supportée - + - Eeprom is from the wrong board - L'EEPROM ne correspond pas au type de radio sélectionné - + - Eeprom backup not supported - Sauvegarde d'EEPROM non supportée - + - Something that couldn't be guessed, sorry - Erreur inconnue - + Warning: Avertissement: - - + + - Your radio probably uses a wrong firmware, eeprom size is 4096 but only the first 2048 are used - Le firmware de la radio est probablement incorrect, @@ -1404,14 +1530,14 @@ Vérifier la sélection (M64/M128) - + - Your eeprom is from an old version of OpenTX, upgrading! - You should 'save as' to keep the old file as a backup. - - Le fichier qui vient d'être ouvert provient d'une ancienne verison d'OpenTX et a été converti. -Il est recommandé d'"Enregistrer Sous" au plus vite pour ne pas risquer d'écraser votre ancien fichier. + To keep your original file as a backup, please choose File -> Save As specifying a different name. + - Votre eeprom provient d'une ancienne version d'OpenTX, mettez à niveau! + Pour conserver une sauvegarde de votre fichier d'origine, choisissez "Fichier → Enregistrer sous" en spécifiant un autre nom. - + Warnings! Avertissements ! @@ -1541,27 +1667,27 @@ Les 2 - + Edit %1 Éditer %1 - + Click to access popup menu Cliquez pour accéder au menu contextuel - + Clear All Effacer Tout - + Set All Définir Tout - + Invert All Inverser Tout @@ -2073,6 +2199,14 @@ + Flight mode + + + FM + PV + + + FlightMode @@ -2098,47 +2232,69 @@ FlightModePanel - + Rotary Encoder %1 Sélecteur Rotatif %1 - + Name Nom - + Value source Source valeur - + Value Valeur - + + Unit + + + + + Prec + + + + + Min + Min + + + + Max + Max + + + GVAR%1 VG%1 - + Popup enabled Indication activée - + + &Clear &Effacer - + + Clear Effacer - + Clear all current Flight Mode properties? Effacer tout les modes de vols ? @@ -2146,17 +2302,17 @@ FlightModesPanel - + Flight Mode %1 Phase de vol %1 - + (%1) - + (default) (par défaut) @@ -2598,7 +2754,7 @@ - + ms @@ -2631,7 +2787,7 @@ - + <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0//EN" "http://www.w3.org/TR/REC-html40/strict.dtd"> <html><head><meta name="qrichtext" content="1" /><style type="text/css"> p, li { white-space: pre-wrap; } @@ -2681,7 +2837,7 @@ Luminosité écran éteint - + Mode selection: Mode 1: @@ -2722,271 +2878,296 @@ - + Mode 1 (RUD ELE THR AIL) Mode 1 (DIR PRF GAZ AIL) - + Mode 2 (RUD THR ELE AIL) Mode 2 (DIR GAZ PRF AIL) - + Mode 3 (AIL ELE THR RUD) Mode 3 (AIL PRF GAZ DIR) - + Mode 4 (AIL THR ELE RUD) Mode 4 (AIL GAZ PRF DIR) - + <html><head/><body><p>Channel order</p><p><br/></p><p>Defines the order of the default mixes created on a new model.</p></body></html> <html><head/><body><p>Ordre des voies</p><p><br/></p><p>Détermine l'ordre des mixages par défaut sur un nouveau modèle.</p></body></html> - + R E T A D P G A - + R E A T D P A G - + R T E A D G P A - + R T A E D G A P - + R A E T D A P G - + R A T E D A G P - + E R T A P D G A - + E R A T P D A G - + E T R A P G D A - + E T A R P G A D - + E A R T P A D G - + E A T R P A G D - + T R E A G D P A - + T R A E G D A P - + T E R A G P D A - + T E A R G P A D - + T A R E G A D P - + T A E R G A P D - + A R E T A D P G - + A R T E A D G P - + A E R T A P D G - + A E T R A P G D - + A T R E A G D P - + A T E R A G P D - + + USB Mode + Mode USB + + + + Ask on Connect + Demander à la connexion + + + + Joystick (HID) + + + + + USB Mass Storage + Stockage USB (SD) + + + + USB Serial (CDC) + Port série USB (Debug) + + + Stick Mode Mode - + Metric Métrique - + Imperial Impérial - + Default Channel Order Ordre des voies par défaut - + GPS Coordinates Coordonnées GPS - + Min - - + + v - + Max - - Low Memory Warning - Alerte mémoire pleine + + RSSI Poweroff Warning + Désactiver avertissement RSSI - + Inactivity Timer Alerte d'inactivité - + Show Splash Screen on Startup Afficher l'écran de démarrage - + Contrast Contraste - + Battery Meter Range Plage de l'indicateur de batterie - + Haptic Strength Puissance vibreur - + LCD Display Type Type de LCD - + "No Sound" Warning Alerte "son coupé" - + Battery Warning Alerte batterie - + Haptic Length Durée vibreur - + MAVLink Baud Rate Baudrate Mavlink - - + + Quiet Mode silencieux - + Only Alarms Seulement les alarmes - - + + No Keys Touches silencieuses - - + + All Tous - + Battery warning voltage. This is the threashhold where the battery warning sounds. @@ -2997,115 +3178,116 @@ Plage de valeurs: 5v...10v - + Standard - + Optrex - + If not zero will sound beeps if the transmitter has been left without inputs for the specified number of minutes. Si différent de 0, émission d'un bip sonore régulier si aucune action n'a été effectuée sur l'émetteur depuis le temps spécifié (en minutes). Réinitialisation en agissant sur n'importe lequel des manches / touches de navigation. - + min - - + + Show splash screen on startup Affiche l'écran d'accueil au démarrage - + --- - + 2s - + 3s - + 4s - + 6s - + 8s - + 10s - + 15s - + 4800 Baud - + 9600 Baud - + 14400 Baud - + 19200 Baud - + 38400 Baud - + 57600 Baud - + 76800 Baud - + 115200 Baud - - + + + <!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0//EN" "http://www.w3.org/TR/REC-html40/strict.dtd"> <html><head><meta name="qrichtext" content="1" /><style type="text/css"> p, li { white-space: pre-wrap; } @@ -3130,72 +3312,77 @@ <p style=" margin-top:0px; margin-bottom:0px; margin-left:0px; margin-right:0px; -qt-block-indent:0; text-indent:0px;">Alerte mode silencieux - Avertissement si les bips sont désactivés</p></body></html> - - + + X-Short Très court - - + + Short Court - - + + Normal - - + + Long - - + + X-Long Très long - + hh° (N/S) mm' ss''.dd - + + Low EEPROM Warning + Avertissement EEPROM faible + + + NMEA - + Play Delay (switch mid position) Délai position centrale inters - + Measurement Units Unités de mesure - + Haptic Mode Mode du vibreur - + Beeper Length Durée des bips - + Beeper Mode Réglage des bips - + Beeper volume 0 - Quiet. No beeps at all. @@ -3212,7 +3399,7 @@ Extra long : bips extra longs. - + Alarms Only Seulement les Alarmes @@ -3220,7 +3407,7 @@ GeneralSetupPanel - + If you enable FAI, you loose the vario, the play functions, the telemetry screen. This function cannot be disabled by the radio. Are you sure ? @@ -3228,6 +3415,14 @@ + Global Variable + + + GV + VG + + + GyroPage @@ -3656,28 +3851,36 @@ + Input + + + I + E + + + InputsPanel - + Move Up Monter - + Ctrl+Up Ctrl+Haut - + Move Down Descendre - + Ctrl+Down Ctrl+Bas @@ -3687,97 +3890,105 @@ Effacer toutes les entrées - + Not enough available inputs! Pas assez d'entrées disponibles ! - + Delete Selected Inputs? Supprimer les entrées sélectionnées ? - + &Add &Ajouter - + Ctrl+A Ctrl+A - + &Edit &Édition - + Enter Entrée - + &Delete &Supprimer - + Delete Supprimer - + &Copy &Copier - + Ctrl+C - + &Cut &Couper - + Ctrl+X - + &Paste &Coller - + Ctrl+V - + Du&plicate Du&pliquer - + Ctrl+U - + Clear Inputs? Effacer toutes les entrées ? - + Really clear all the inputs? Voulez-vous vraiment effacer toutes les entrées ? + Logic Switch + + + L + + + + LogicalSwitchesPanel @@ -3810,28 +4021,18 @@ ET supplémentaire - - L%1 - IL%1 - - (instant) - + &Delete &Supprimer - - Delete - Supprimer - - - + &Copy &Copier @@ -3842,30 +4043,15 @@ (infini) - - Ctrl+C - - - - + &Cut &Couper - - Ctrl+X - - - - + &Paste &Coller - - - Ctrl+V - - LogsDialog @@ -3875,32 +4061,37 @@ Visualiseur de Log - + Filename Nom de fichier - + Open LogFile Ouvrir fichier de Log - + Zoom - + + Save session CSV + Sauvegarder la session CSV + + + X - + Y - + Reset Remise à zéro @@ -3920,42 +4111,42 @@ Heure (hh:mm:ss) - + Plot Title Change Changer le titre du graphique - + New plot title: Nouveau nom de graphique: - + Axis Label Change Changer le nom de l'axe - + New axis label: Nouveau nom d'axe: - + Graph Name Change Changer le nom de la série - + New graph name: Nouveau nom de série: - + Error: no GPS data not found Erreur: Aucune donnée GPS trouvée - + The column containing GPS coordinates must be named "GPS". The columns for altitude "GAlt" and for speed "GSpd" are optional @@ -3964,79 +4155,79 @@ Les colonnes contenant l'altitude "GAlt" et la vitesse "GSpd" sont optionnelles - + Error Erreur - + Cannot write file %1: %2. Ecriture fichier %1 impossible: %2. - + Cursor A: %1 m Curseur A: %1 m - + Cursor B: %1 m Curseur B: %1 m - + Time delta: %1 Ecart temps:%1 - + Climb rate: %1 m/s Taux monté : %1 m/s - + Select your log file Sélectionnez votre fichier log - + Available fields Champs disponibles - + The selected logfile contains %1 invalid lines out of %2 total lines Le fichier de log sélectionné contient %1 lignes invalides sur %2 - + total duration durée totale - + duration durée - + (L1) - + (R1) - + (L2) - + (R2) @@ -4056,59 +4247,59 @@ Fichier - + New release available Nouvelle version disponible - - + + Error Erreur - + Error opening file %1: %2. Erreur à l'ouverture du fichier %1: %2. - + Compilation server too busy, try later Serveur de compilation surchargé, veuillez réessayer plus tard - + Unknown server failure, try later Erreur inconnue du serveur de compilation, veuillez réessayer plus tard - + Do you want to write the firmware to the radio now ? Voulez vous transférer le firmware à la radio maintenant ? - - + + Yes Oui - - + + No Non - - + + Release Notes Notes de version - - + + Do you want to download release %1 now ? Voulez-vous télécharger la version %1 maintenant ? @@ -4138,7 +4329,7 @@ Thème avec icônes monochromes noires - + Firmware %1 does not seem to have ever been downloaded. Release %2 is available. Do you want to download it now? @@ -4151,7 +4342,7 @@ Nous recommandons de lire attentivement les notes de version à l'aide du bouton ci-dessous, celles-ci peuvent contenir des infos importantes concernant les changements effectués depuis la version précédente. - + A new version of %1 firmware is available: - current is %2 - newer is %3 @@ -4290,7 +4481,7 @@ Transférer les réglages et modèles vers la radio - + Companion @@ -4388,7 +4579,7 @@ Ecrire - + A new version of Companion is available (version %1)<br>Would you like to download it? Une nouvelle version de Companion est disponible (version %1)<br>Voulez-vous la télécharger ? @@ -4413,7 +4604,7 @@ Afficher la fenêtre "A propos" de l'application - + File loaded Fichier chargé @@ -4436,37 +4627,37 @@ Lire les réglages et modèles depuis la radio - + Ignore this release %1? Ignorer la version %1 ? - + Not enough flash available on this board for all the selected options Pas assez de place disponible pour les options sélectionnées - + Compilation server temporary failure, try later Erreur de compilation sur le serveur, veuillez réessayer plus tard - + Compilation error Erreur de compilation - + Invalid firmware Firmware invalide - + Invalid board Carte non valide - + Invalid language Language non valide @@ -4583,12 +4774,12 @@ Classique - + Show this message again at next startup? Afficher ce message lors du prochain démarrage ? - + A new release of Companion is available, please check the <a href='%1'>OpenTX website!</a> Une nouvelle version de Companion est disponible, vérifiez le site OpenTX <a href='%1'> !</a> @@ -4953,19 +5144,19 @@ Lister les programmateurs supportés - - + + Save As Enregistrer Sous - - + + No updates available at this time. Aucune mise à jour disponible. - + Unable to check for updates. Impossible de rechercher des mises à jour. @@ -4976,7 +5167,7 @@ Aide - + Checking for updates Recherche de mises à jour @@ -5589,27 +5780,27 @@ Nom - + DEST -> %1 - + Click to access popup menu Cliquez pour accéder au menu contextuel - + Clear All Effacer Tout - + Set All Définir Tout - + Invert All Inverser Tout @@ -5630,28 +5821,51 @@ + MixersListWidget + + + Increase font size + Augmenter la taille de la police + + + + Decrease font size + Diminuer la taille de la police + + + + Default font size + Taille de la police par défaut + + + + Ctrl+0 + + + + MixesPanel - + Move Up Monter - + Ctrl+Up Ctrl+Haut - + Move Down Descendre - + Ctrl+Down Ctrl+Bas @@ -5661,102 +5875,102 @@ Effacer tous les mixages - + Not enough available mixers! Plus de mixages disponibles ! - + Delete Selected Mixes? Supprimer les mixages sélectionnés ? - + &Add &Ajouter - + Ctrl+A - + &Edit &Édition - + Enter Entrée - + Ctrl+T - + &Toggle highlight &(Dé)sélectionner - + &Delete &Supprimer - + Delete Supprimer - + &Copy &Copier - + Ctrl+C - + Ctrl+X - + C&ut &Couper - + &Paste &Coller - + Ctrl+V - + Du&plicate &Dupliquer - + Ctrl+U - + Clear Mixes? Effacer tous les mixages ? - + Really clear all the mixes? Êtes-vous sûr de vraiment vouloir effacer tous les mixages ? @@ -5827,293 +6041,334 @@ ModelPrinter - + %1 bytes %1 octets - + Exponential Exponentiel - + Extra Fine Extra fin - + Fine Fin - + Medium Moyen - + Coarse Grossier - + Unknown Inconnu - + Enabled Actif - + Disabled Inactif - + + 10mW + + + + + 100mW + + + + + + 500mW + + + + + 1W + + + + + 25mW + + + + %1, Channels(%2-%3), PPM delay(%4usec), Pulse polarity(%5) %1, Voies(%2-%3), Impulsion(%4µs), Polarité(%5) - + %1, Channels(%2-%3) %1, Voies(%2-%3) - + Receiver number(%1) No. de récepteur(%1) - + radio Protocol %1, subType %2, option value %3 radio Protocol %1, sousType %2, option %3 - + + Module Type: %1, Power: %2, Telemetry Enabled: %3 + Type Module: %1, Puissance: %2, Télémétrie Activée: %3 + + + Slave/Jack Elève/Jack - + Master/SBUS Module Maître/SBUS module - + Master/CPPM Module Maître/CPPM Module - + Master/SBUS in battery compartment Maître/SBUS compartiment batterie - + Master/Jack Maître/Jack - + 90 - + 120 - + 120X - + 140 - + Rudder Dérive - + Elevator Profondeur - + Throttle Gaz - + Aileron Ailerons - + Name(%1) Nom(%1) - + Persistent Persistant - + MinuteBeep Bip minutes - + CountDown(Beeps) Cpte à rebours(bips) - + CountDown(Voice) Cpte à rebours(voix) - + CountDown(Haptic) Cpte à rebours(vibreur) - - + + Off - - - - + + + + FM%1 PV%1 - + FM%1%2 PV%1%2 - + FM%1+%2 PV%1+%2 - + Weight Ratio - + Switch Inter - - + + NoTrim Pas de trim - + Weight(%1) Ratio(%1) - + Switch(%1) Inter(%1) - + No DR/Expo Pas d'expo/DR - - + + Offset(%1) Décalage(%1) - + + Y + O + + + + N + + + + Delay(u%1:d%2) Délai(h%1:b%2) - + Slow(u%1:d%2) Ralenti(h%1:b%2) - + Warn(%1) Alerte(%1) - + Disabled in all flight modes Désactivé pour toutes les phases de vol - + Flight modes(%1) Phases de vol(%1) - + Flight mode(%1) Phase de vol(%1) - + Edge(%1, [%2:%3]) Flanc(%1, [%2:%3]) - + instant - + Sticky(%1, %2) Bistable(%1, %2) - + Timer(%1, %2) Chrono(%1, %2) - + Duration(%1s) Durée(%1s) - + Delay(%1s) Délai(%1s) - + Custom Prédéfini - + Standard @@ -6149,243 +6404,273 @@ Module - + Failsafe Mode Mode Failsafe - + Start 1ère voie - + PPM delay Impulsion - + Negative Négative - + Positive - + Polarity Polarité - + Trainer Mode Mode écolage - + PPM Frame Length Longueur de trame PPM - + CH VOIE - + Antenna Antenne - + Internal Interne - + Ext. + Int. Ext. + Int. - + Option value - + us µs - + Master/Jack Maître/Jack - + Slave/Jack Elève/Jack - + Master/SBUS Module Maître/SBUS module - + Master/CPPM Module Maître/CPPM Module - + Master/SBUS in battery compartment Maître/SBUS dans compartiment batterie - + + RF Output Power + Puissance RF + + + + 10 mW + + + + + 100 mW + + + + + 500 mW + + + + + 1000 mW + + + + + Sub Type + Sous-Type + + + + Module Telemetry + Télémétrie Module + + + Show values in: Afficher les valeurs en: - + % abbreviation for percent - + μs abbreviation for microseconds - + ms - + Channels Nb de voies - + Not set Non défini - + Hold Maintien - + Custom Prédéfini - + No Pulses Pas d'impulsions - + Receiver Récepteur - + Failsafe Positions - Positions + Positions Failsafe - + Protocol Protocole - + Multi Radio Protocol - Protocol Multi + Protocole Multi - + Receiver No. Récepteur No. - + Output type Type de sortie - + Open Drain - + Push Pull - - SubType - SousType - - - + Bind on startup Bind au démarage - + Low Power - Puiss Réd + Puissance Réduite ModulePanel - + Trainer Port Port écolage - + Internal Radio System Module HF interne - + External Radio Module Module HF externe - - + + Radio System Module HF - + Extra Radio System Module HF supplémentaire - + Value Valeur - + Hold Maintien - + No Pulse Pas d'impulsion @@ -6489,7 +6774,7 @@ - + Flight mode Phase de vol @@ -6510,129 +6795,153 @@ - + FM%1 PV%1 + + Global variables + Variables globales + + - + GV%1 VG%1 - + RE%1 - - Limits - Limites - - - + Channel Voie - - + + Direct + + + + + Curve + Courbe + + + + PPM + + + + + Linear + Linéaire + + + Offset Décalage - + Min - - Max - + + Outputs + Sorties - - Invert - Inversé + + Subtrim + Subtrim + + + + Max + - + Global Variables Variables globales - + Inputs Entrées - + Mixers Mixages - + Curves Courbes - + L%1 - IL%1 + - + Logical Switches Inters logiques - + SF%1 FS%1 - + Special Functions Fonctions spéciales - + Telemetry Settings Paramètres de télémesure - + Analogs Analogiques - + Unit Unité - + Scale Echelle - + A%1 - + RSSI Alarms Alarmes RSSI - + Low Alarm Alarme basse - + Critical Alarm Alarme critique @@ -6784,646 +7093,609 @@ QObject - + Polish Polonais - - CH%1 - VOIE%1 - - - + No Non - + RotEnc A Sel.Rot. A - + Rot Enc B Sel.Rot. B - + Rot Enc C Sel.Rot. C - + Rot Enc D Sel.Rot. D - + Rot Enc E Sel.Rot. E - + Trainer Écolage - + Trainer RUD Écolage Direction - + Trainer ELE Écolage Profondeur - + Trainer THR Écolage Gaz - + Trainer AIL Écolage Ailerons - + Instant Trim Trims instantanés - + Play Sound Jouer Son - + Haptic Vibreur - + S3 - + RSSI Tx - + RSSI Rx - + A3 - + A4 - + Cells Velm - + dTE - + Hdg Cap - + AirSpeed Vitesse Air - + A3- - + A4- - + Speed+ Vit+ - + Dist+ - + AirSpeed+ VitA+ - + Cell- Elem- - + Cells- Velm- - + Vfas- - + Curr+ Cour+ - + Powr+ Puis+ - + ACC - + GPS Time Heure GPS - + L1 - + L2 - - [I%1] - [E%1] - - - + LUA%1%2 - - TR%1 - - - - - FM0 - PV0 - - - - FM1 - PV1 - - - - FM2 - PV2 - - - - FM3 - PV3 - - - - FM4 - PV4 - - - - FM5 - PV5 - - - - FM6 - PV6 - - - - FM7 - PV7 - - - - FM8 - PV8 - - - + Trim 5 Down Trim 5 Bas - + Trim 5 Up Trim 5 Haut - + Trim 6 Down Trim 6 Bas - + Trim 6 Up Trim 6 Haut - + One Un - + a>x - + a<x - + |a|>x - + |a|<x - + AND ET - + OR OU - + XOR OUX - + a=b - + a!=b - + a>b - + a<b - + a>=b - + a<=b - + d>=x - + |d|>=x - + a=x - + a~x - + Timer Chrono - + Sticky Bistable - + + ? + + + + + + 0._ + + + + + + 0.0 + + + + + ?.? + + + + Left Horizontal Gauche Horizontal - + Left Vertical Gauche Vertical - + Right Vertical Droit Vertical - + Right Horizontal Droit Horizontal - + Aux. 1 - + Aux. 2 - - + + Unknown Inconnu - + SD Logs Logs SD - + Adjust %1 Ajuster %1 - + played once, not during startup !1x Lu une fois, mais pas à la mise en route - + repeat(%1s) Répéter chaque %1s - + DISABLED DESACTIVE - + INV - + NOR - + Reset Remise à zéro - + Set Timer %1 Définir chrono %1 - + Vario - + Volume - + Play Value Lire valeur - + Backlight Rétroéclairage - + Play Track Jouer fichier - - + + --- - + English Anglais - + French Français - + Italian Italien - + German Allemand - + Czech Tchèque - + Slovak Slovaque - + Spanish Espagnol - + Portuguese Portugais - + Swedish Suédois - + Dutch Hollandais - + Hungarian Hongrois - + No repeat 1x Lu une fois - + Play Both Jouer les 2 - + Override %1 Remplacer %1 - + Play Script Exécuter script - + Screenshot Capture d'écran - + Background Music Musique de fond - + Background Music Pause Pause musique de fond - + Edge Flanc - - - + + + <font color=red><b>Inconsistent parameter</b></font> <font color=red><b>Paramètre inconsistant</b></font> - + + Telemetry Télémesure - + Value Valeur - + Decr: Décr: - + Incr: Incr: - + Played once, not during startup 1x Lu une fois, mais pas à la mise en route - + %1s - + Value Valeur - + Source - + GVAR VG - + Increment Incrément - + Flight Vol @@ -7439,1390 +7711,1376 @@ Valeur de la phase de vol %1 - + Keys Touches - + Sticks Manches - + Keys + Sticks Touches + manches - + SetFailsafe Int. Module Déf. failsafe module interne - + SetFailsafe Ext. Module Déf. failsafe module externe - + RangeCheck Int. Module Test portée module interne - + RangeCheck Ext. Module Test portée module externe - + Bind Int. Module Bind module interne - + Bind Ext. Module Bind module externe - + Rotary Encoder Sélecteur Rotatif - + Yellow Jaune - + Orange Orange - + Red Rouge - + Winged Shadow How High - + Winged Shadow How High (not supported) Winged Shadow How High (non supporté) - + FrSky Sensor Hub Sensor Hub FrSky - + None Aucun - + Imperial Impérial - + Metric Métrique - + Uknown error during Simulator startup. Erreur inconnue pendant le démarrage du simulateur. - + Simulator Error Erreur Simulateur - + Data Load Error Erreur de lecture des données - + Error occurred while starting simulator. Une erreur s'est produite lors du démarrage du simulateur. - - GV%1 - VG%1 - - - - - + + + ---- - + THR GAZ - - + + Batt - + SWR - + P1 - - - - - - - + + + + + + + V - - + + s - + ft - - - + + + m - - + + °C - - + + ° - - + + + + % - - - + + + mph - - - + + + km/h - - + + m/s - - + + A - + °F - - + + mAh - - + + W - - + + g - + P2 - + P3 - + MAX - - - LSw%1 - IL%1 - - - + RudTrim Left TrmD Gauche - + RudTrim Right TrmD Droite - + EleTrim Down TrmP Bas - + EleTrim Up TrmP Haut - + ThrTrim Down TrmG Bas - + ThrTrim Up TrmG Haut - + AilTrim Left TrmA Gauche - + AilTrim Right TrmA Droite - + THs GZs - + TH% GZ% - + THt GZt - - + + ??? - + Diff(%1) - + Expo(%1) - + Function(%1) Fonction(%1) - + Curve(%1) Courbe(%1) - + Rud Dir - + Ele Prf - + Thr Gaz - + Ail Ail - + TrmR TrmD - + TrmE TrmP - + TrmT TrmG - + TrmA TrmA - - - + + + S1 - + mA - + kts - + f - + mW mW - + dB - + rpms - + Rad - + hours heures - + minutes - + seconds secondes - + h:m - + m:s - + h:m:s - - - + + + S2 - - - + + + LS - - - + + + RS - + F1 - + F2 - + F3 - + F4 - - - + + + REa - - - + + + REb - + Trm5 - + Trm6 - - - + + + Timer3 Chrono 3 - + Alt Altitude - + Rpm - + Fuel Carburant - + Speed Vitesse - + Dist Distance - + GPS Alt Altitude GPS - + Cell Element LiPo - + Vfas Vfas - + Curr Courant - + Cnsp Consommation - + Powr Puissance - + AccX - + AccY - + AccZ - + VSpd Vitesse Verticale - + A1- - + A2- - + Alt- - + Alt+ - + Rpm+ - + T1+ - + T2+ - - + + Time Temps - + CYC%1 - - - + + + ON - - - + + + OFF - - + + Support for frsky telemetry mod Support de la télémétrie FrSky - - + + Support for jeti telemetry mod Support de la télémétrie JETI - - + + Support for receiving ardupilot data Support de la télémétrie ARDUPILOT - - + + Support for receiving NMEA data Support de la télémétrie NMEA - + Support for telemetry easy board Support de la carte TelemetrEZ - - + + Support for MAVLINK devices Support du protocole MAVLINK - + Rotary Encoder use in menus navigation Utiliser le sélecteur rotatif pour la navigation - - - - - - + + + + + + Enable heli menu and cyclic mix support Activer le menu hélico et les mixages CCPM - - - - - - + + + + + + Enable TEMPLATES menu Inclure les gabarits - + 6P - + Enable Lua compiler Active le compilateur Lua - + Support for the DIY-Multiprotocol-TX-Module Support du module Multiprotocol - + Unknown error Erreur inconnue - + ... plus %1 errors ... plus %1 erreurs - + Cannot write radio settings Impossible d'écrire les paramètres de la radio - + Cannot write model %1 Impossible d'écrire le modèle %1 - + JSx - + JSy - + + Enable Lua custom scripts screen + Activer l'écran des scripts Lua personnalisés + + + Enable bindings options Activer les options de Bind (désactiver la télémétrie pour les XSR, etc...) - + KS108 LCD - + WTV20 voice module Module voix WTV20 - + JQ6500 voice module Module voix JQ6500 - + FrSky Taranis X9D+ - + FrSky Taranis X9D - + Horus gimbals installed (Hall sensors) Manches à effet HALL de Horus installés - - FrSky Taranis X7 - - - - - FrSky Horus + + FrSky Taranis X7 / X7S - + Use ONLY with first DEV pcb version Exclusivement pour les Horus DEV - + Turnigy 9XR-PRO - + Turnigy 9XR with m128 chip Turnigy 9XR avec une puce m128 - - - - + + + + No splash screen Pas d'écran de démarrage - - - - - - + + + + + + Disable curves menus Désactiver le menu des courbes - - - - - + + + + + Support for radio modified with regular speaker Haut-parleur au lieu du buzzer d'origine - - - - - + + + + + Used if you have modified your radio with voice mode Support du module vocal - - - - - + + + + + Used if you have modified your radio with haptic mode Support du vibreur - + Channel values displayed in us Positions de voies affichées en µs - - - - - - - - - + + + + + + + + + Battery graph Graphique de batterie - - - - - - - - - - - + + + + + + + + + + + Use alternative SQT5 font Utiliser la police alternative SQT5 - + Possibility to enable FAI MODE (no telemetry) at field Possibilité d'activer le mode FAI (télémétrie désactivée) sur le terrain - + FAI MODE (no telemetry) always enabled Mode FAI (télémétrie désactivée) toujours actif - - Instead of Joystick emulation, USB connection is Mass Storage (as in the Bootloader) - Le port USB connecte les disques virtuels au lieu du Joystick (comme dans le bootloader) - - - - Instead of Joystick emulation, USB connection is Command Line Interface - Le port USB est utilisé pour un port série avec interface par ligne de commande au lieu du Joystick - - - + Removes D8 FrSky protocol support which is not legal for use in the EU on radios sold after Jan 1st, 2015 Masque le protocole D8. Légalement obligatoire sur les radios Européennes importées après le 1er janvier 2015 - - + + Support for PPM internal module hack Support du remplacement du module interne par un module PPM - + ST7565P LCD or compatible ST7565P LCD ou compatible - + ST7565R LCD or compatible ST7565R LCD ou compatible - + ERC12864FSF LCD LCD ERC12864FSF - + ST7920 LCD LCD ST7920 - - - - + + FrSky Horus X10 / X10S + + + + + FrSky Horus X12S + + + + + + + Enable the throttle trace in Statistics Activer l'historique du manche des gaz dans les statistiques - + EEprom write progress bar Barre de progression pour l'écriture de l'EEPROM - - + + No Winged Shadow How High support Supprimer le support du variomètre Winged Shadow How High - + Turnigy 9XR - - + + No vario support Supprimer la fonction variomètre audio - - + + No GPS support Supprimer le support du GPS - - + + No gauges in the custom telemetry screen Supprimer l'affichage des valeurs de télémesure par barres - + 9X with stock board 9X avec carte mère d'origine - + Allow compensating for offset errors in FrSky FAS current sensors Permettre la compensation d'un décalage des capteurs de courant FASxx FrSky - - + + Add support for reversing stick inputs (e.g. needed for FrSky gimbals) Ajoute le support de l'inversion des manches (nécessaire pour l'utilisation de manches FrSky) - + DIY MEGA2560 radio - + Power management by soft-off circuitry Gestion alim. par software - + FrSky Taranis X9E - + Confirmation before radio shutdown Confirmation avant l'arrêt de la radio - + Haptic module installed Module vibreur installé - - Support for Lua model scripts - Support des scripts Lua - - - - + + Support of FrSky PXX protocol Support du protocole PXX FrSky - + Disable HELI menu and cyclic mix support Supprimer le menu HELICO et les mixages cycliques - + Disable Global variables Supprimer le support des variables globales - - - - - + + + + + Support for DSM2 modules Support du protocole DSM2 - - - - - - + + + + + + PPM center adjustment in limits Neutres PPM ajustables - - - - - - + + + + + + Symetrical Limits Limites symétriques - - - - - - - + + + + + + + Pots use in menus navigation Support de la navigation dans les menus avec les POTS - + No OverrideCH functions available Désactive la fonction spéciale "Remplacer VOIEx" - - - - - - - - - + + + + + + + + + No flight modes Pas de phases de vol - - + + SmartieParts 2.2 Backlight support Support du rétroéclairage pour la carte SmartieParts 2.2 - - - - - - + + + + + + Enable resetting values by pressing up and down at the same time Permet la remise à zéro des valeurs en pressant haut-bas en même temps, valeur min avec gauche/bas, valeur max avec haut/droite, inversion avec gauche/droite - - - - - - - - - + + + + + + + + + No graphical check boxes and sliders Pas de cases à cocher et de curseurs graphiques - - - - - - - - - + + + + + + + + + Don't use bold font for highlighting active items Ne pas mettre les lignes actives en gras - - - - - + + + + + EEprom write Progress bar Barre de progression affichée lors des écritures EEPROM - - - - - - + + + + + + Imperial units Unités Impériales - - - + + + Bluetooth interface Interface Bluetooth - - - - - - - - - + + + + + + + + + Global variables Variables globales - - - - - - - - - + + + + + + + + + In model setup menus automatically set source by moving the control Sélectionner les sources des mixeurs en bougeant le contrôle désiré - - - - - - - - - + + + + + + + + + In model setup menus automatically set switch by moving the control Sélectionner les interrupteurs en bougeant le contrôle désiré - + 9X with stock board and m128 chip Carte 9x avec un chip m128 - + 9X with AR9X board 9X avec carte AR9X - + 9X with Sky9x board 9X avec carte Sky9x - + 9X with Gruvin9x board 9X avec carte Gruvin9x - - + + Support for SD memory card Support de la carte SD - + Support for DSM2 modules using ppm instead of true serial Support pour les modules DSM2 par le signal PPM - - - + + + Enable HELI menu and cyclic mix support Activer le menu hélico et les mixages CCPM - - - + + + Timer1 Chrono 1 - - - + + + Timer2 Chrono 2 - + A1 - + A2 - + T1 - + T2 - - + + Warning Avertissement - + Simulator for this firmware is not yet available Le simulateur n'est pas encore disponible pour ce firmware - + Switch Inter - + Switch L'inter - + cannot be exported on this board! n'est pas supporté sur cette carte ! - + Source %1 cannot be exported on this board! La source %1 n'est pas supportée sur cette plateforme ! - + OpenTX only accepts %1 points in all curves OpenTX n'accepte que %1 points au maximum entre toutes les courbes - + OpenTx only accepts %1 points in all curves OpenTX n'accepte que %1 points au maximum entre toutes les courbes - - - - - - + + + + + + OpenTX on this board doesn't accept this function OpenTX ne supporte pas cette fonction sur cette carte - + OpenTX doesn't accept this telemetry protocol OpenTX ne supporte pas ce protocole de télémesure - - - + + + OpenTX doesn't accept this radio protocol OpenTX ne supporte pas ce protocole radio - + OpenTX doesn't allow this number of channels OpenTX ne supporte pas ce nombre de voies - + Trim disabled Trim désactivé - + Own Trim Valeur indépendante - + Use Trim from Flight mode %1 Utiliser le trim de la phase de vol %1 - + Use Trim from Flight mode %1 + Own Trim as an offset Utiliser le trim de la phase de vol %1 + une valeur indépendante additionnée @@ -8852,7 +9110,7 @@ - + @@ -8891,12 +9149,12 @@ Impossible de trouver la carte SD Horus ! - + Positive - + Negative Négative @@ -8917,7 +9175,7 @@ - + Models Translators do NOT use accent for this, this is the default category name on Horus. Modeles @@ -9056,6 +9314,13 @@ Conversion error on field %1 Erreur de conversion du champ %1 + + + We have found existing settings for Companion version: %1. +Do you want to import them? + Nous avons trouvé des paramètres existants pour Companion version: %1. +Voulez-vous les importer ? + RadioKnobWidget @@ -9235,47 +9500,47 @@ Image du modèle - + Exponential Exponentiel - + Throttle Trim Idle Only Trim ralenti uniquement - + Timer 3 Chrono 3 - + Extra Fine Extra fin - + Fine Fin - + Medium Moyen - + Coarse Grossier - + Display Checklist Afficher la checklist - + Timer 2 Chrono 2 @@ -9285,37 +9550,42 @@ Chrono 1 - + Never Jamais - + On change Au changement - + Always Toujours - + Global Functions Fonctions globales - + + Edit Checklist... + Éditer Checklist... + + + Throttle Source Source des gaz - + Trim Step Pas des trims - + Trims Display Affichage des trims @@ -9355,22 +9625,22 @@ Modèle - + Extended Limits Débattements étendus - + Extended Trims Trims étendus - + Throttle Warning Alerte gaz - + Reverse throttle operation. If this is checked the throttle will be reversed. Idle will be forward, trim will also be reversed and the throttle warning will be reversed as well. @@ -9381,7 +9651,7 @@ - + Reverse Throttle Gaz inversés @@ -9389,7 +9659,7 @@ SetupPanel - + Timer %1 Chrono %1 @@ -9600,106 +9870,111 @@ SimulatorMain - + + OpenTx Simulator + Simulateur OpenTX + + + Available profiles: Profils disponibles: - + ID: - + Name: Nom: - + Available radios: Radio disponibles: - + Radio profile ID or Name to use for simulator. ID ou nom du profil radio pour le simulateur. - + profile profil - + Radio type to simulate (usually defined in profile). Type de radio à simuler (souvent défini dans le profil). - + radio - + Directory containing the SD card image to use. The default is configured in the chosen Radio Profile. Répertoire contenant l'image de la carte SD. La valeur par défaut est configurée dans le profil radio sélectionné. - + path chemin - + Data source type to use (applicable to Horus only). One of: Type de source de données à utiliser (applicable uniquement à la Horus). Un des: - + type - + data-source source-données - + Radio data (.bin/.eeprom/.otx) image file to use OR data folder path (for Horus-style radios). NOTE: any existing EEPROM data incompatible with the selected radio type may be overwritten! Fichier de données utilisé (.bin/.eeprom/.otx) OU chemin du répertoire de données (pour les radios de type Horus). NOTE: toutes les données EEPROM existantes non compatible avec le type de radio sélectionné peuvent être écrasées ! - + [data-source] [source-données] - + Error: Profile ID %1 was not found. Erreur: ID Profil %1 non trouvé. - + Unrecognized startup data source type: %1 Type de données source non reconnue au démarrage: %1 - + WARNING: couldn't initialize SDL: %1 ATTENTION: erreur initialisation SDL: %1 - + ERROR: No simulator libraries available. ERREUR: pas de simulateur disponible. - + ERROR: Couldn't start simulator, missing radio/profile/data file/folder. Profile ID: [%1]; Radio ID: [%2]; Data File: [%3] @@ -9708,14 +9983,14 @@ Fichier de Données: [%3] - + ERROR: Radio profile or simulator firmware not found. Profile ID: [%1]; Radio ID: [%2] ERREUR: Profil radio ou firmware du simulateur non trouvé Profil ID: [%1]; Radio ID: [%2] - + Uknown error during Simulator startup. Erreur inconnue pendant le démarrage du simulateur. @@ -9873,74 +10148,74 @@ Défini la hauteur du widget radio comme étant une taille fixe. - + ERROR: Failed to create simulator interface, possibly missing or bad library. ERREUR: Impossible de créer l'interface du simulateur, bibliothèque éventuellement manquante ou mauvaise. - + Alt+T - + Radio Outputs Sorties de la radio - + F2 - + Telemetry Simulator Simulateur de télémesure - + F4 - + Trainer Simulator Simulateur d'écolage - + F5 - + Debug Output Fenêtre de débogage - + F6 - + <b>Simulator Controls:</b> <b>Commandes simulateur:</b> - + <tr><th>Key/Mouse</th><th>Action</th></tr> note: must match html layout of each table row (keyTemplate). <tr><th>Touche/Souris</th><th>Action</th></tr> - + <tr><td><kbd>%1</kbd></td><td>%2</td></tr> note: must match html layout of help text table header. - + Simulator Help Aide du simulateur @@ -10083,67 +10358,67 @@ Simulateur Radio (%1) - + Could not determine startup data source. Impossible de déterminer les données source. - + Could not load data, possibly wrong format. Impossible de charger les données, mauvais format. - + Data Load Error Erreur de lecture des données - + Invalid startup data provided. Plese specify a proper file/path. Données de démarrage fournies non valides. Veuillez spécifier un fichier/chemin approprié. - + Simulator Startup Error Erreur de démarrage du simulateur - + Error saving data: could open file for writing: '%1' Erreur de sauvegarde des données: impossible d'écrire le fichier '%1' - + Error saving data: could not get data from simulator interface. Erreur de sauvegarde des données: impossible de récupérer les données depuis l'interface de simulation. - + An unexpected error occurred while attempting to save radio data to file '%1'. Une erreur inattendue s'est produite lors de l'enregistrement des données radio dans le fichier '%1'. - + Data Save Error Erreur de sauvegarde des données - + Warning Avertissement - + Cannot open joystick, joystick disabled Impossible d'accéder au Joystick, Joystick désactivé - + Radio firmware error: %1 Erreur firmware radio: %1 - + - Flight Mode %1 (#%2) - Phase de Vol %1 (#%2) @@ -10355,66 +10630,66 @@ Telemetry - + A1 - + A2 - + RSSI - + Alarm 1 Alarme 1 - - + + ---- ---- - - + + Yellow Jaune - - + + Orange Orange - - + + Red Rouge - + Alarm 2 Alarme 2 - + Serial Protocol Protocole Série - + Volt source Source de mesure de tension - + Current source Source de mesure de courant @@ -10424,115 +10699,126 @@ Protocole - + None Aucun - + FrSky Sensor Hub Sensor Hub FrSky - + Blades Pales - + Sink Max Chute max - + Climb Max Montée max - + Sink Min Chute min - + Climb Min Montée min - + Center Silent Neutre silencieux - + Vario source Source vario - + Vario limits Limites vario - + + Disable telemetry audio warnings + Désactiver les avertissements audio de la télémétrie + + + Altimetry Altitude - + Altitude source Source de l'altitude - + Volts source Source de la tension - + Top Bar Barre de titre de l'écran d'accueil - + mAh - + A - + Various Divers - + Sensors Capteurs - + Disable multi sensor handling Désactiver la gestion des capteurs multiples - + mAh count Valeur enregistrée - + FAS Offset Décalage FAS - + Persistent mAh Mémorisation des mAh + + + + TELE + + TelemetryAnalog @@ -10719,79 +11005,79 @@ Ecran de télémesure %1 - + Low Alarm Alarme basse - + Critical Alarm Alarme critique - + Winged Shadow How High - + Winged Shadow How High (not supported) Winged Shadow How High (non supporté) - + Alti Alt - + Alti+ Alt+ - + VSpeed Vitesse verticale - - - + + + A1 - - - + + + A2 - - + + A3 - - + + A4 - - + + FAS - + Cells Velm - + --- @@ -11407,17 +11693,17 @@ Transmet les valeurs non vides au simulateur. - + Log File Fichier de Log - + LOG Files (*.csv) Fichier LOG (*.csv) - + ERROR - invalid file ERREUR - fichier non valide @@ -11673,37 +11959,37 @@ TimerPanel - + Silent Aucun - + Beeps Bips - + Voice Voix - + Haptic Vibreur - + Not persistent Non persistant - + Persistent (flight) Persistant (vol) - + Persistent (manual reset) Persistant (RAZ manuelle) @@ -11830,6 +12116,11 @@ Ail + + + TR + + TrainerSimulator @@ -12340,29 +12631,29 @@ Configuration de SAM-BA - - - + + + Select Location Choisir l'emplacement - + List available programmers Lister les programmateurs supportés - + Avrdude help Aide d'AVRDUDE - + Companion - + <b><u>WARNING!</u></b><br>Normally CPU type is automatically selected according to the chosen firmware.<br>If you change the CPU type the resulting eeprom could be inconsistent. <b><u>ATTENTION !</u></b><br>Le type de processeur est normalement choisi automatiquement pour le firmware sélectionné.<br>Si vous le changez, l'EEPROM peut être corrompue lors du transfert. diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/src/wizarddata.cpp opentx-companion22-2.2.1~ppa01~xenial/companion/src/wizarddata.cpp --- opentx-companion22-2.2.0~ppa02~xenial/companion/src/wizarddata.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/src/wizarddata.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -61,7 +61,7 @@ void WizMix::addMix(ModelData &model, Input input, int weight, int channel, int & mixIndex) { if (input != NO_INPUT) { - bool isHorusOrTaranis = IS_HORUS_OR_TARANIS(getCurrentBoard()); + bool isHorusOrTaranis = IS_ARM(getCurrentBoard()); if (input >= RUDDER_INPUT && input <= AILERONS_INPUT) { MixData & mix = model.mixData[mixIndex++]; mix.destCh = channel+1; @@ -119,7 +119,7 @@ // Add the Throttle Cut option if( options[THROTTLE_CUT_OPTION] && throttleChannel >=0 ){ model.customFn[switchIndex].swtch.type = SWITCH_TYPE_SWITCH; - model.customFn[switchIndex].swtch.index = IS_HORUS_OR_TARANIS(getCurrentBoard()) ? SWITCH_SF0 : SWITCH_THR; + model.customFn[switchIndex].swtch.index = IS_ARM(getCurrentBoard()) ? SWITCH_SF0 : SWITCH_THR; model.customFn[switchIndex].enabled = 1; model.customFn[switchIndex].func = (AssignFunc)throttleChannel; model.customFn[switchIndex].param = -100; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/targets/windows/companion-vs.nsi.in opentx-companion22-2.2.1~ppa01~xenial/companion/targets/windows/companion-vs.nsi.in --- opentx-companion22-2.2.0~ppa02~xenial/companion/targets/windows/companion-vs.nsi.in 2017-05-14 17:18:57.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/targets/windows/companion-vs.nsi.in 2017-10-31 16:16:43.000000000 +0000 @@ -77,13 +77,13 @@ !define MUI_FINISHPAGE_NOAUTOCLOSE !define MUI_FINISHPAGE_RUN !define MUI_FINISHPAGE_RUN_CHECKED - !define MUI_FINISHPAGE_RUN_TEXT "Launch OpenTX Companion @VERSION_FAMILY@" !define MUI_FINISHPAGE_RUN_FUNCTION "LaunchLink" # !define MUI_FINISHPAGE_SHOWREADME_NOTCHECKED # !define MUI_FINISHPAGE_SHOWREADME $INSTDIR\readme.txt !insertmacro MUI_PAGE_FINISH !insertmacro MUI_UNPAGE_CONFIRM + !insertmacro MUI_UNPAGE_COMPONENTS !insertmacro MUI_UNPAGE_INSTFILES ;-------------------------------- @@ -95,7 +95,7 @@ ;-------------------------------- ;Installer Sections -Section "OpenTX Companion" SecDummy +Section "OpenTX Companion @VERSION_FAMILY@" SecDummy Delete "$INSTDIR\opentx-*-simulator.dll" Delete "$INSTDIR\lang\*.*" @@ -125,6 +125,8 @@ File "@QT_DLL_DIR@\Qt5Multimedia.dll" File "@QT_DLL_DIR@\Qt5Svg.dll" File "@QT_DLL_DIR@\Qt5Xml.dll" + File "@PYTHON_DIRECTORY@\lib\site-packages\PyQt4\libeay32.dll" + File "@PYTHON_DIRECTORY@\lib\site-packages\PyQt4\ssleay32.dll" File "@SDL_DIR@\SDL.dll" File "@CMAKE_CURRENT_SOURCE_DIR@\..\targets\windows\avrdude.exe" @@ -139,6 +141,14 @@ SetOutPath "$INSTDIR\imageformats" File "@QT_DLL_DIR@\..\plugins\imageformats\qjpeg.dll" File "@QT_DLL_DIR@\..\plugins\imageformats\qsvg.dll" + File "@QT_DLL_DIR@\..\plugins\imageformats\qdds.dll" + File "@QT_DLL_DIR@\..\plugins\imageformats\qgif.dll" + File "@QT_DLL_DIR@\..\plugins\imageformats\qicns.dll" + File "@QT_DLL_DIR@\..\plugins\imageformats\qico.dll" + File "@QT_DLL_DIR@\..\plugins\imageformats\qtga.dll" + File "@QT_DLL_DIR@\..\plugins\imageformats\qtiff.dll" + File "@QT_DLL_DIR@\..\plugins\imageformats\qwbmp.dll" + File "@QT_DLL_DIR@\..\plugins\imageformats\qwebp.dll" SetOutPath "$INSTDIR\mediaservice" File "@QT_DLL_DIR@\..\plugins\mediaservice\dsengine.dll" @@ -189,7 +199,9 @@ ;-------------------------------- ;Uninstaller Section -Section "Uninstall" +Section "un.OpenTX Companion @VERSION_FAMILY@" + + SectionIn RO ; Not deselectable ;ADD YOUR OWN FILES HERE... @@ -214,6 +226,8 @@ Delete "$INSTDIR\libusb0.dll" Delete "$INSTDIR\dfu-util.exe" Delete "$INSTDIR\libusb-1.0.dll" + Delete "$INSTDIR\libeay32.dll" + Delete "$INSTDIR\ssleay32.dll" Delete "$INSTDIR\Uninstall.exe" Delete "$INSTDIR\lang\*.*" @@ -243,9 +257,11 @@ Delete "$SMPROGRAMS\$StartMenuFolder\Uninstall Companion @VERSION_FAMILY@.lnk" RMDir "$SMPROGRAMS\$StartMenuFolder" - DeleteRegKey /ifempty HKCU "Software\OpenTX Companion @VERSION_FAMILY@" DeleteRegKey HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\OpenTX Companion @VERSION_FAMILY@" +SectionEnd +Section /o "un.Settings" + DeleteRegKey HKCU "Software\OpenTX\Companion @VERSION_FAMILY@" SectionEnd Function LaunchLink diff -Nru opentx-companion22-2.2.0~ppa02~xenial/companion/targets/windows/license.txt opentx-companion22-2.2.1~ppa01~xenial/companion/targets/windows/license.txt --- opentx-companion22-2.2.0~ppa02~xenial/companion/targets/windows/license.txt 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/companion/targets/windows/license.txt 2017-11-11 11:29:14.000000000 +0000 @@ -1,4 +1,4 @@ -Copyright 2011-2016 OpenTX team +Copyright © 2011-2017 OpenTX team OpenTX Companion is based on code named eePe by author - Erez Raviv diff -Nru opentx-companion22-2.2.0~ppa02~xenial/CREDITS.txt opentx-companion22-2.2.1~ppa01~xenial/CREDITS.txt --- opentx-companion22-2.2.0~ppa02~xenial/CREDITS.txt 2017-05-31 19:49:19.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/CREDITS.txt 2017-12-17 16:22:27.000000000 +0000 @@ -39,6 +39,7 @@ RC Studio (monthly) Craft & Theory (monthly) OpenTX Manuals by Lothar Thole +Team BlackSheep [People who have donated to OpenTX] Mario Sette @@ -665,7 +666,7 @@ Bryan Anderson Daniel Garber Pavel Stein -Ravi Gupta +RCdiy Patrick Tuxbury Mark Deverell John Capell @@ -843,7 +844,6 @@ NorthSide Hannes Mössler James Kaufman -Ravi Gupta Lexington S Morley Ralph Segar Frédéric Devillard @@ -978,7 +978,6 @@ Wolfgang Renisch Trevor Hinze Mohammad Zargari -Dr. Willutzki Jean Pierre Bernard Patrick Castellan Udo Tödter @@ -1220,3 +1219,89 @@ Jörgen Norman Chen Zhongzhong Eddie Ehlin +Evening Shade Pottery +Michel Vanaken +Forgues Research +Hike For Happiness +Vegar Elde +Anindya Mukerjee +Fabrice Debonnet +Darko Perković +Leonard MacKey +James A Davey +Matthias Häusel +Thierry Laligand +Pascal Gelis +Christelle Boudet +Damir Pooshs +Bertrand Brunner +Alexander Mathis +Jean-Luc Le Goff +Allan Abbott +Paul Elstob +Mark Levine +K L Wolfbrandt +Jeffrey Horton +Erlendur Konradsson +Dennis Miller +Шарлаимов Константин +Philippe Roussely +Michel Gutierrez +Joel Meziere +Widco Us +Marcos Guimaraes +Olivier Petri +Alfredo Mac Donald +Erich Strebel +Robert Goillandeau +Joel Lopez +Morten Myklebust +Ferenc Kunkli +Josh Kraker +Roger Bergevin +Geoff Sim +Arthur Reynolds +David Dalley +Colin Macdonald +Charles Wilson +Walter Daser +CG Tech Inc +Alexander Röhlich +Peter Goodrich +Randy Melton +Paul Pridday +Jörgen Norman +Peter Glassey +Carlos Vicente +Nael Bishtawi +Paul Dr. Willutzki +Heart of NM LLC +Ulf Hedlund +Meinolph Kaufmann +Bill Keenan +Ralf Kosel +Lukas Hucik +Uwe Jordt +Tuan Le +Burt Pickard-Richardson +Robert Rubio +Merv Dale +Michel Garbarino +Geoff Graham +Georges Pezet +Robert Wilhelm +Francis Herzog +Bo Hjeresen +Danny Koch +John Eppling +Thierry Malosse +Johann Antretter +Jan Kaiser +Rachel Berkhahn +Luca Massimiliano Comolli +Mario Wesierski +Evening Shade Pottery +Jean Desmet +Alexis Pons +Roger Bergevin +Eddie Ehlin diff -Nru opentx-companion22-2.2.0~ppa02~xenial/debian/changelog opentx-companion22-2.2.1~ppa01~xenial/debian/changelog --- opentx-companion22-2.2.0~ppa02~xenial/debian/changelog 2017-05-31 20:38:42.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/debian/changelog 2017-12-17 16:39:34.000000000 +0000 @@ -1,3 +1,15 @@ +opentx-companion22 (2.2.1~ppa01~xenial) xenial; urgency=low + + * New release 2.2.1~ppa01 + + -- projectkk2glider Sun, 17 Dec 2017 17:32:44 +0100 + +opentx-companion22 (2.2.1~N432+test01~xenial) xenial; urgency=low + + * New release 2.2.1~N432+test01 + + -- projectkk2glider Fri, 10 Nov 2017 18:55:08 +0100 + opentx-companion22 (2.2.0~ppa02~xenial) xenial; urgency=low * New release 2.2.0~ppa02 diff -Nru opentx-companion22-2.2.0~ppa02~xenial/debian/suffix opentx-companion22-2.2.1~ppa01~xenial/debian/suffix --- opentx-companion22-2.2.0~ppa02~xenial/debian/suffix 2017-05-31 20:38:42.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/debian/suffix 2017-12-17 16:39:34.000000000 +0000 @@ -1 +1 @@ -suffix=ppa02 +suffix=ppa01 diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/CROSSFIRE/crossfire.lua opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/CROSSFIRE/crossfire.lua --- opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/CROSSFIRE/crossfire.lua 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/CROSSFIRE/crossfire.lua 2017-10-31 16:16:43.000000000 +0000 @@ -0,0 +1,121 @@ +---- ######################################################################### +---- # # +---- # Copyright (C) OpenTX # +-----# # +---- # License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html # +---- # # +---- # This program is free software; you can redistribute it and/or modify # +---- # it under the terms of the GNU General Public License version 2 as # +---- # published by the Free Software Foundation. # +---- # # +---- # 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. # +---- # # +---- ######################################################################### +local devices = { } +local lineIndex = 1 +local pageOffset = 0 + +local function createDevice(id, name) + local device = { + id = id, + name = name, + timeout = 0 + } + return device +end + +local function getDevice(name) + for i=1, #devices do + if devices[i].name == name then + return devices[i] + end + end + return nil +end + +local function parseDeviceInfoMessage(data) + local id = data[2] + local name = "" + local i = 3 + while data[i] ~= 0 do + name = name .. string.char(data[i]) + i = i + 1 + end + local device = getDevice(name) + if device == nil then + device = createDevice(id, name) + devices[#devices + 1] = device + end + local time = getTime() + device.timeout = time + 3000 -- 30s + if lineIndex == 0 then + lineIndex = 1 + end +end + +local devicesRefreshTimeout = 0 +local function refreshNext() + local command, data = crossfireTelemetryPop() + if command == nil then + local time = getTime() + if time > devicesRefreshTimeout then + devicesRefreshTimeout = time + 100 -- 1s + crossfireTelemetryPush(0x28, { 0x00, 0xEA }) + end + elseif command == 0x29 then + parseDeviceInfoMessage(data) + end +end + +local function selectDevice(step) + lineIndex = 1 + ((lineIndex + step - 1 + #devices) % #devices) +end + +-- Init +local function init() + lineIndex = 0 + pageOffset = 0 +end + +NoCross = { 110, LCD_H - 28, "Waiting for Crossfire devices...", TEXT_COLOR + INVERS + BLINK } + +-- Main +local function run(event) + if event == nil then + error("Cannot be run as a model script!") + return 2 + elseif event == EVT_EXIT_BREAK then + return 2 + elseif event == EVT_ROT_LEFT then + selectDevice(1) + elseif event == EVT_ROT_RIGHT then + selectDevice(-1) + end + + lcd.clear() + lcd.drawFilledRectangle(0, 0, LCD_W, 30, TITLE_BGCOLOR) + lcd.drawText(1, 5,"CROSSFIRE SETUP", MENU_TITLE_COLOR) + + + if #devices == 0 then + lcd.drawText(NoCross[1],NoCross[2],NoCross[3],NoCross[4]) + else + for i=1, #devices do + local attr = (lineIndex == i and INVERS or 0) + if event == EVT_ROT_BREAK and attr == INVERS then + crossfireTelemetryPush(0x28, { devices[i].id, 0xEA }) + return "device.lua" + end + lcd.drawText(5, i*22+10, devices[i].name, attr) + end + end + + refreshNext() + + return 0 +end + +return { init=init, run=run } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/CROSSFIRE/device.lua opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/CROSSFIRE/device.lua --- opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/CROSSFIRE/device.lua 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/CROSSFIRE/device.lua 2017-10-31 16:16:43.000000000 +0000 @@ -0,0 +1,533 @@ +---- ######################################################################### +---- # # +---- # Copyright (C) OpenTX # +-----# # +---- # License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html # +---- # # +---- # This program is free software; you can redistribute it and/or modify # +---- # it under the terms of the GNU General Public License version 2 as # +---- # published by the Free Software Foundation. # +---- # # +---- # 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. # +---- # # +---- ######################################################################### +local deviceId = 0 +local deviceName = "" +local lineIndex = 0 +local pageOffset = 0 +local edit = false +local charIndex = 1 +local fieldPopup +local fieldTimeout = 0 +local fieldId = 1 +local fieldChunk = 0 +local fieldData = {} +local fields = {} + +local function getField(line) + local counter = 1 + for i = 1, #fields do + local field = fields[i] + if not field.hidden then + if counter < line then + counter = counter + 1 + else + return field + end + end + end +end + +local function initLineIndex() + lineIndex = 0 + for i = 1, #fields do + local field = getField(i) + if field and field.type ~= 11 and field.type ~= 12 and field.name ~= nil then + lineIndex = i + break + end + end +end + +-- Change display attribute to current field +local function incrField(step) + local field = getField(lineIndex) + if field.type == 10 then + local byte = 32 + if charIndex <= #field.value then + byte = string.byte(field.value, charIndex) + step + end + if byte < 32 then + byte = 32 + elseif byte > 122 then + byte = 122 + end + if charIndex <= #field.value then + field.value = string.sub(field.value, 1, charIndex-1) .. string.char(byte) .. string.sub(field.value, charIndex+1) + else + field.value = field.value .. string.char(byte) + end + else + local min, max = 0, 0 + if field.type <= 5 then + min = field.min + max = field.max + step = field.step * step + elseif field.type == 9 then + min = 0 + max = #field.values - 1 + end + if (step < 0 and field.value > min) or (step > 0 and field.value < max) then + field.value = field.value + step + end + end +end + +-- Select the next or previous editable field +local function selectField(step) + local newLineIndex = lineIndex + local field + repeat + newLineIndex = newLineIndex + step + if newLineIndex == 0 then + newLineIndex = #fields + elseif newLineIndex == 1 + #fields then + newLineIndex = 1 + pageOffset = 0 + end + field = getField(newLineIndex) + until newLineIndex == lineIndex or (field and field.type ~= 11 and field.name) + lineIndex = newLineIndex + if lineIndex > 11 + pageOffset then -- NOTE: increased from 7 to 11 to allow 11 lines in Horus display + pageOffset = lineIndex - 11 -- NOTE: increased from 7 to 11 to allow 11 lines in Horus display + elseif lineIndex <= pageOffset then + pageOffset = lineIndex - 1 + end +end + +local function split(str) + local t = {} + local i = 1 + for s in string.gmatch(str, "([^;]+)") do + t[i] = s + i = i + 1 + end + return t +end + +local function fieldGetString(data, offset) + local result = "" + while data[offset] ~= 0 do + result = result .. string.char(data[offset]) + offset = offset + 1 + end + offset = offset + 1 + return result, offset +end + +local function parseDeviceInfoMessage(data) + local offset + deviceId = data[2] + deviceName, offset = fieldGetString(data, 3) + local fields_count = data[offset+12] + for i=1, fields_count do + fields[i] = { name=nil } + end +end + +local function fieldGetValue(data, offset, size) + local result = 0 + for i=0, size-1 do + result = bit32.lshift(result, 8) + data[offset + i] + end + return result +end + +local function fieldUnsignedLoad(field, data, offset, size) + field.value = fieldGetValue(data, offset, size) + field.min = fieldGetValue(data, offset+size, size) + field.max = fieldGetValue(data, offset+2*size, size) + field.default = fieldGetValue(data, offset+3*size, size) + field.unit, offset = fieldGetString(data, offset+4*size) + field.step = 1 +end + +local function fieldUnsignedToSigned(field, size) + local bandval = bit32.lshift(0x80, (size-1)*8) + field.value = field.value - bit32.band(field.value, bandval) * 2 + field.min = field.min - bit32.band(field.min, bandval) * 2 + field.max = field.max - bit32.band(field.max, bandval) * 2 + field.default = field.default - bit32.band(field.default, bandval) * 2 +end + + local function fieldSignedLoad(field, data, offset, size) + fieldUnsignedLoad(field, data, offset, size) + fieldUnsignedToSigned(field, size) +end + +local function fieldIntSave(index, value, size) + local frame = { deviceId, 0xEA, index } + for i=size-1, 0, -1 do + frame[#frame + 1] = (bit32.rshift(value, 8*i) % 256) + end + crossfireTelemetryPush(0x2D, frame) +end + +local function fieldUnsignedSave(field, size) + local value = field.value + fieldIntSave(field.id, value, size) +end + +local function fieldSignedSave(field, size) + local value = field.value + if value < 0 then + value = bit32.lshift(0x100, (size-1)*8) + value + end + fieldIntSave(field.id, value, size) +end + +local function fieldIntDisplay(field, y, attr) + -- lcd.drawNumber(140, y, field.value, LEFT + attr) -- NOTE: original code getLastPos not available in Horus + -- lcd.drawText(lcd.getLastPos(), y, field.unit, attr) -- NOTE: original code getLastPos not available in Horus + lcd.drawText(140, y, field.value .. field.unit, attr) -- NOTE: Concenated fields instead of get lastPos +end + +-- UINT8 +local function fieldUint8Load(field, data, offset) + fieldUnsignedLoad(field, data, offset, 1) +end + +local function fieldUint8Save(field) + fieldUnsignedSave(field, 1) +end + +-- INT8 +local function fieldInt8Load(field, data, offset) + fieldSignedLoad(field, data, offset, 1) +end + +local function fieldInt8Save(field) + fieldSignedSave(field, 1) +end + +-- UINT16 +local function fieldUint16Load(field, data, offset) + fieldUnsignedLoad(field, data, offset, 2) +end + +local function fieldUint16Save(field) + fieldUnsignedSave(field, 2) +end + +-- INT16 +local function fieldInt16Load(field, data, offset) + fieldSignedLoad(field, data, offset, 2) +end + +local function fieldInt16Save(field) + fieldSignedSave(field, 2) +end + +-- FLOAT +local function fieldFloatLoad(field, data, offset) + field.value = fieldGetValue(data, offset, 4) + field.min = fieldGetValue(data, offset+4, 4) + field.max = fieldGetValue(data, offset+8, 4) + field.default = fieldGetValue(data, offset+12, 4) + fieldUnsignedToSigned(field, 4) + field.prec = data[offset+16] + if field.prec > 2 then + field.prec = 2 + end + field.step = fieldGetValue(data, offset+17, 4) + field.unit, offset = fieldGetString(data, offset+21) +end + +local function fieldFloatDisplay(field, y, attr) + local attrnum + if field.prec == 1 then + attrnum = LEFT + attr + PREC1 + elseif field.prec == 2 then + attrnum = LEFT + attr + PREC2 + else + attrnum = LEFT + attr + end + -- lcd.drawNumber(140, y, field.value, attrnum) -- NOTE: original code getLastPos not available in Horus + -- lcd.drawText(lcd.getLastPos(), y, field.unit, attr) -- NOTE: original code getLastPos not available in Horus + lcd.drawText(140, y, field.value .. field.unit, attr) -- NOTE: Concenated fields instead of get lastPos +end + +local function fieldFloatSave(field) + fieldUnsignedSave(field, 4) +end + +-- TEXT SELECTION +local function fieldTextSelectionLoad(field, data, offset) + local values + values, offset = fieldGetString(data, offset) + if values ~= "" then + field.values = split(values) + end + field.value = data[offset] + field.min = data[offset+1] + field.max = data[offset+2] + field.default = data[offset+3] + field.unit, offset = fieldGetString(data, offset+4) +end + +local function fieldTextSelectionSave(field) + crossfireTelemetryPush(0x2D, { deviceId, 0xEA, field.id, field.value }) +end + +local function fieldTextSelectionDisplay(field, y, attr) + -- lcd.drawText(140, y, field.values[field.value+1], attr) -- NOTE: original code getLastPos not available in Horus + -- lcd.drawText(lcd.getLastPos(), y, field.unit, attr) -- NOTE: original code getLastPos not available in Horus + lcd.drawText(140, y, field.values[field.value+1] .. field.unit, attr) -- NOTE: Concenated fields instead of get lastPos +end + +-- STRING +local function fieldStringLoad(field, data, offset) + field.value, offset = fieldGetString(data, offset) + if #data >= offset then + field.maxlen = data[offset] + end +end + +local function fieldStringSave(field) + local frame = { deviceId, 0xEA, field.id } + for i=1, string.len(field.value) do + frame[#frame + 1] = string.byte(field.value, i) + end + frame[#frame + 1] = 0 + crossfireTelemetryPush(0x2D, frame) +end + +local function fieldStringDisplay(field, y, attr) + if edit == true and attr then + -- lcd.drawText(140, y, field.value, FIXEDWIDTH) -- NOTE: FIXEDWIDTH unknown.... + -- lcd.drawText(134+6*charIndex, y, string.sub(field.value, charIndex, charIndex), FIXEDWIDTH + attr) -- NOTE: FIXEDWIDTH unknown.... + lcd.drawText(140, y, field.value, attr) + lcd.drawText(134+6*charIndex, y, string.sub(field.value, charIndex, charIndex), attr) + else + lcd.drawText(140, y, field.value, attr) + end +end + +local function fieldCommandLoad(field, data, offset) + field.status = data[offset] + field.timeout = data[offset+1] + field.info, offset = fieldGetString(data, offset+2) + if field.status < 2 or field.status > 3 then + fieldPopup = nil + end +end + +local function fieldCommandSave(field) + if field.status == 0 then + field.status = 1 + crossfireTelemetryPush(0x2D, { deviceId, 0xEA, field.id, field.status }) + fieldPopup = field + fieldTimeout = getTime() + field.timeout + end +end + +local function fieldCommandDisplay(field, y, attr) + lcd.drawText(1, y, field.name, attr) + if field.info ~= "" then + lcd.drawText(140, y, "[" .. field.info .. "]") + end +end + +local functions = { + { load=fieldUint8Load, save=fieldUint8Save, display=fieldIntDisplay }, + { load=fieldInt8Load, save=fieldInt8Save, display=fieldIntDisplay }, + { load=fieldUint16Load, save=fieldUint16Save, display=fieldIntDisplay }, + { load=fieldInt16Load, save=fieldInt16Save, display=fieldIntDisplay }, + nil, + nil, + nil, + nil, + { load=fieldFloatLoad, save=fieldFloatSave, display=fieldFloatDisplay }, + { load=fieldTextSelectionLoad, save=fieldTextSelectionSave, display=fieldTextSelectionDisplay }, + { load=fieldStringLoad, save=fieldStringSave, display=fieldStringDisplay }, + nil, + { load=fieldStringLoad, save=fieldStringSave, display=fieldStringDisplay }, + { load=fieldCommandLoad, save=fieldCommandSave, display=fieldCommandDisplay }, +} + +local function parseParameterInfoMessage(data) + if data[2] ~= deviceId or data[3] ~= fieldId then + fieldData = {} + fieldChunk = 0 + return + end + local field = fields[fieldId] + local chunks = data[4] + for i=5, #data do + fieldData[#fieldData + 1] = data[i] + end + if chunks > 0 then + fieldChunk = fieldChunk + 1 + else + fieldChunk = 0 + field.id = fieldId + field.parent = fieldData[1] + field.type = fieldData[2] % 128 + field.hidden = (bit32.rshift(fieldData[2], 7) == 1) + local name, i = fieldGetString(fieldData, 3) + if name ~= "" then + local indent = "" + local parent = field.parent + while parent ~= 0 do + indent = indent .. " " + parent = fields[parent].parent + end + field.name = indent .. name + end + if functions[field.type+1] then + functions[field.type+1].load(field, fieldData, i) + end + if not fieldPopup then + if lineIndex == 0 and field.hidden ~= true and field.type and field.type ~= 11 and field.type ~= 12 then + initLineIndex() + end + fieldId = 1 + (fieldId % #fields) + end + fieldData = {} + end +end + +local function refreshNext() + local command, data = crossfireTelemetryPop() + if command == nil then + local time = getTime() + if fieldPopup then + if time > fieldTimeout then + local frame = { deviceId, 0xEA, fieldPopup.id } + crossfireTelemetryPush(0x2D, frame) + fieldTimeout = time + fieldPopup.timeout + end + elseif time > fieldTimeout and not edit then + crossfireTelemetryPush(0x2C, { deviceId, 0xEA, fieldId, fieldChunk }) + fieldTimeout = time + 200 -- 2s + end + elseif command == 0x29 then + parseDeviceInfoMessage(data) + elseif command == 0x2B then + parseParameterInfoMessage(data) + fieldTimeout = 0 + end +end + +-- Main +local function runDevicePage(event) + if event == EVT_EXIT_BREAK then -- exit script + if edit == true then + edit = false + local field = getField(lineIndex) + fieldTimeout = getTime() + 200 -- 2s + fieldId, fieldChunk = field.id, 0 + fieldData = {} + functions[field.type+1].save(field) + else + return "crossfire.lua" + end + elseif event == EVT_ROT_BREAK then -- toggle editing/selecting current field + local field = getField(lineIndex) + if field.name then + if field.type == 10 then + if edit == false then + edit = true + charIndex = 1 + else + charIndex = charIndex + 1 + end + elseif field.type < 11 then + edit = not edit + end + if edit == false then + fieldTimeout = getTime() + 200 -- 2s + fieldId, fieldChunk = field.id, 0 + fieldData = {} + functions[field.type+1].save(field) + end + end + elseif edit then + if event == EVT_ROT_LEFT then + incrField(1) + elseif event == EVT_ROT_RIGHT then + incrField(-1) + end + else + if event == EVT_ROT_RIGHT then + selectField(1) + elseif event == EVT_ROT_LEFT then + selectField(-1) + end + end + + lcd.clear() + lcd.drawFilledRectangle(0, 0, LCD_W, 30, TITLE_BGCOLOR) + lcd.drawText(1, 5,deviceName, MENU_TITLE_COLOR) + + for y = 1, 11 do + local field = getField(pageOffset+y) + if not field then + break + elseif field.name == nil then + lcd.drawText(1, y*22+10, "...") + else + local attr = lineIndex == (pageOffset+y) and ((edit == true and BLINK or 0) + INVERS) or 0 + lcd.drawText(1, y*22+10, field.name) + if functions[field.type+1] then + functions[field.type+1].display(field, y*22+10, attr) + end + end + end + + return 0 +end + +local function runPopupPage(event) + local result + if fieldPopup.status == 3 then + result = popupConfirmation(fieldPopup.info, event) + else + result = popupWarning(fieldPopup.info, event) + end + if result == "OK" then + crossfireTelemetryPush(0x2D, { deviceId, 0xEA, fieldPopup.id, 4 }) + elseif result == "CANCEL" then + crossfireTelemetryPush(0x2D, { deviceId, 0xEA, fieldPopup.id, 5 }) + end + return 0 +end + +-- Init +local function init() + lineIndex, edit = 0, false +end + +-- Main +local function run(event) + if event == nil then + error("Cannot be run as a model script!") + return 2 + end + + local result + if fieldPopup ~= nil then + result = runPopupPage(event) + else + result = runDevicePage(event) + end + + refreshNext() + + return result +end + +return { init=init, run=run } Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/S6R/img/back.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/S6R/img/back.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/S6R/img/delta_b.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/S6R/img/delta_b.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/S6R/img/done.bmp and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/S6R/img/done.bmp differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/S6R/img/down.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/S6R/img/down.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/S6R/img/forward.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/S6R/img/forward.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/S6R/img/left.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/S6R/img/left.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/S6R/img/plane_b.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/S6R/img/plane_b.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/S6R/img/planev_b.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/S6R/img/planev_b.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/S6R/img/planev_s.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/S6R/img/planev_s.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/S6R/img/right.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/S6R/img/right.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/S6R/img/up.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/S6R/img/up.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/S6R/img/vert.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/S6R/img/vert.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/S6R/img/vert-r.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/S6R/img/vert-r.png differ diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/S6R/S6R_Calibrate.lua opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/S6R/S6R_Calibrate.lua --- opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/S6R/S6R_Calibrate.lua 2017-05-14 17:18:57.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/S6R/S6R_Calibrate.lua 1970-01-01 00:00:00.000000000 +0000 @@ -1,340 +0,0 @@ -local VALUE = 0 -local COMBO = 1 - -local COLUMN_2 = 300 - -local edit = false -local page = 1 -local current = 1 -local refreshState = 0 -local refreshIndex = 0 -local calibrationState = 0 -local pageOffset = 0 -local calibrationStep = 0 -local pages = {} -local fields = {} -local modifications = {} -local wingBitmaps = {} -local mountBitmaps = {} -local calibBitmaps = {} - -local configFields = { - {"Wing type:", COMBO, 0x80, nil, { "Normal", "Delta", "VTail" } }, - {"Mounting type:", COMBO, 0x81, nil, { "Horz", "Horz rev.", "Vert", "Vert rev." } }, -} -local calibrationPositions = { "up", "down", "left", "right", "forward", "back" } -local wingBitmapsFile = {"img/plane_b.png", "img/delta_b.png", "img/planev_b.png"} -local mountBitmapsFile = {"img/up.png", "img/down.png", "img/vert.png", "img/vert-r.png"} -local calibBitmapsFile = {"img/up.png", "img/down.png", "img/left.png", "img/right.png", "img/forward.png", "img/back.png"} - -local settingsFields = { - {"S6R functions:", COMBO, 0x9C, nil, { "Disable", "Enable" } }, - {"CH5 mode:", COMBO, 0xA8, nil, { "AIL2", "AUX1" } }, - {"CH6 mode:", COMBO, 0xA9, nil, { "ELE2", "AUX2" } }, - {"AIL direction:", COMBO, 0x82, nil, { "Normal", "Invers" }, { 255, 0 } }, - {"ELE direction:", COMBO, 0x83, nil, { "Normal", "Invers" }, { 255, 0 } }, - {"RUD direction:", COMBO, 0x84, nil, { "Normal", "Invers" }, { 255, 0 } }, - {"AIL2 direction:", COMBO, 0x9A, nil, { "Normal", "Invers" }, { 255, 0 } }, - {"ELE2 direction:", COMBO, 0x9B, nil, { "Normal", "Invers" }, { 255, 0 } }, - {"AIL stabilize gain:", VALUE, 0x85, nil, 0, 200, "%"}, - {"ELE stabilize gain:", VALUE, 0x86, nil, 0, 200, "%"}, - {"RUD stabilize gain:", VALUE, 0x87, nil, 0, 200, "%"}, - {"AIL auto level gain:", VALUE, 0x88, nil, 0, 200, "%"}, - {"ELE auto level gain:", VALUE, 0x89, nil, 0, 200, "%"}, - {"ELE upright gain:", VALUE, 0x8C, nil, 0, 200, "%"}, - {"RUD upright gain:", VALUE, 0x8D, nil, 0, 200, "%"}, - {"AIL crab gain:", VALUE, 0x8E, nil, 0, 200, "%"}, - {"RUD crab gain:", VALUE, 0x90, nil, 0, 200, "%"}, - {"AIL auto angle offset:", VALUE, 0x91, nil, -20, 20, "%", 0x6C}, - {"ELE auto angle offset:", VALUE, 0x92, nil, -20, 20, "%", 0x6C}, - {"ELE upright angle offset:", VALUE, 0x95, nil, -20, 20, "%", 0x6C}, - {"RUD upright angle offset:", VALUE, 0x96, nil, -20, 20, "%", 0x6C}, - {"AIL crab angle offset:", VALUE, 0x97, nil, -20, 20, "%", 0x6C}, - {"RUD crab angle offset:", VALUE, 0x99, nil, -20, 20, "%", 0x6C}, -} - -local calibrationFields = { - {"X:", VALUE, 0x9E, 0, -100, 100, "%"}, - {"Y:", VALUE, 0x9F, 0, -100, 100, "%"}, - {"Z:", VALUE, 0xA0, 0, -100, 100, "%"} -} - -local function drawScreenTitle(title,page, pages) - lcd.drawFilledRectangle(0, 0, LCD_W, 30, TITLE_BGCOLOR) - lcd.drawText(1, 5, title, MENU_TITLE_COLOR) - lcd.drawText(LCD_W-40, 5, page.."/"..pages, MENU_TITLE_COLOR) -end - --- Change display attribute to current field -local function addField(step) - local field = fields[current] - local min, max - if field[2] == VALUE then - min = field[5] - max = field[6] - elseif field[2] == COMBO then - min = 0 - max = #(field[5]) - 1 - end - if (step < 0 and field[4] > min) or (step > 0 and field[4] < max) then - field[4] = field[4] + step - end -end - --- Select the next or previous page -local function selectPage(step) - page = 1 + ((page + step - 1 + #pages) % #pages) - refreshIndex = 0 - calibrationStep = 0 - pageOffset = 0 -end - --- Select the next or previous editable field -local function selectField(step) - current = 1 + ((current + step - 1 + #fields) % #fields) - if current > 7 + pageOffset then - pageOffset = current - 7 - elseif current <= pageOffset then - pageOffset = current - 1 - end -end - -local function drawProgressBar() - local width = (300 * refreshIndex) / #fields - lcd.drawRectangle(100, 10, 300, 6) - lcd.drawFilledRectangle(102, 13, width, 2); -end - --- Redraw the current page -local function redrawFieldsPage(event) - lcd.clear() - drawScreenTitle("S6R", page, #pages) - - if refreshIndex < #fields then - drawProgressBar() - end - - for index = 1, 10, 1 do - local field = fields[pageOffset+index] - if field == nil then - break - end - - local attr = current == (pageOffset+index) and ((edit == true and BLINK or 0) + INVERS) or 0 - attr = attr + TEXT_COLOR - - lcd.drawText(1, 30+20*index, field[1], TEXT_COLOR) - - if field[4] == nil then - lcd.drawText(COLUMN_2, 30+20*index, "---", attr) - else - if field[2] == VALUE then - lcd.drawNumber(COLUMN_2, 30+20*index, field[4], LEFT + attr) - elseif field[2] == COMBO then - if field[4] >= 0 and field[4] < #(field[5]) then - lcd.drawText(COLUMN_2, 30+20*index, field[5][1+field[4]], attr) - end - end - end - end -end - -local function telemetryRead(field) - return sportTelemetryPush(0x17, 0x30, 0x0C30, field) -end - -local function telemetryWrite(field, value) - return sportTelemetryPush(0x17, 0x31, 0x0C30, field + value*256) -end - -local telemetryPopTimeout = 0 -local function refreshNext() - if refreshState == 0 then - if calibrationState == 1 then - if telemetryWrite(0x9D, calibrationStep) == true then - refreshState = 1 - calibrationState = 2 - telemetryPopTimeout = getTime() + 80 -- normal delay is 500ms - end - elseif #modifications > 0 then - telemetryWrite(modifications[1][1], modifications[1][2]) - modifications[1] = nil - elseif refreshIndex < #fields then - local field = fields[refreshIndex + 1] - if telemetryRead(field[3]) == true then - refreshState = 1 - telemetryPopTimeout = getTime() + 80 -- normal delay is 500ms - end - end - elseif refreshState == 1 then - local physicalId, primId, dataId, value = sportTelemetryPop() - if physicalId == 0x1A and primId == 0x32 and dataId == 0x0C30 then - local fieldId = value % 256 - if calibrationState == 2 then - if fieldId == 0x9D then - refreshState = 0 - calibrationState = 0 - calibrationStep = (calibrationStep + 1) % 7 - end - else - local field = fields[refreshIndex + 1] - if fieldId == field[3] then - local value = math.floor(value / 256) - if field[3] >= 0x9E and field[3] <= 0xA0 then - local b1 = value % 256 - local b2 = math.floor(value / 256) - value = b1*256 + b2 - value = value - bit32.band(value, 0x8000) * 2 - end - if field[2] == COMBO and #field == 6 then - for index = 1, #(field[6]), 1 do - if value == field[6][index] then - value = index - 1 - break - end - end - elseif field[2] == VALUE and #field == 8 then - value = value - field[8] + field[5] - end - fields[refreshIndex + 1][4] = value - refreshIndex = refreshIndex + 1 - refreshState = 0 - end - end - elseif getTime() > telemetryPopTimeout then - refreshState = 0 - calibrationState = 0 - end - end -end - -local function updateField(field) - local value = field[4] - if field[2] == COMBO and #field == 6 then - value = field[6][1+value] - elseif field[2] == VALUE and #field == 8 then - value = value + field[8] - field[5] - end - modifications[#modifications+1] = { field[3], value } -end - --- Main -local function runFieldsPage(event) - if event == EVT_EXIT_BREAK then -- exit script - return 2 - elseif event == EVT_ENTER_BREAK or event == EVT_ROT_BREAK then -- toggle editing/selecting current field - if fields[current][4] ~= nil then - edit = not edit - if edit == false then - updateField(fields[current]) - end - end - elseif edit then - if event == EVT_PLUS_FIRST or event == EVT_ROT_RIGHT or event == EVT_PLUS_REPT then - addField(1) - elseif event == EVT_MINUS_FIRST or event == EVT_ROT_LEFT or event == EVT_MINUS_REPT then - addField(-1) - end - else - if event == EVT_MINUS_FIRST or event == EVT_ROT_RIGHT then - selectField(1) - elseif event == EVT_PLUS_FIRST or event == EVT_ROT_LEFT then - selectField(-1) - end - end - redrawFieldsPage(event) - return 0 -end - -local function runConfigPage(event) - fields = configFields - local result = runFieldsPage(event) - if fields[1][4] ~= nil then - if wingBitmaps[1 + fields[1][4]] == nil then - wingBitmaps[1 + fields[1][4]] = Bitmap.open(wingBitmapsFile[1 + fields[1][4]]) - end - lcd.drawBitmap(wingBitmaps[1 + fields[1][4]], 10, 90) - end - if fields[2][4] ~= nil then - if mountBitmaps[1 + fields[2][4]] == nil then - mountBitmaps[1 + fields[2][4]] = Bitmap.open(mountBitmapsFile[1 + fields[2][4]]) - end - lcd.drawBitmap(mountBitmaps[1 + fields[2][4]], 190, 110) - end - return result -end - -local function runSettingsPage(event) - fields = settingsFields - return runFieldsPage(event) -end - -local function runCalibrationPage(event) - fields = calibrationFields - if refreshIndex == #fields then - refreshIndex = 0 - end - lcd.clear() - drawScreenTitle("S6R", page, #pages) - if(calibrationStep < 6) then - local position = calibrationPositions[1 + calibrationStep] - lcd.drawText(100, 50, "Place the S6R in the following position", TEXT_COLOR) - if calibBitmaps[calibrationStep + 1] == nil then - calibBitmaps[calibrationStep + 1] = Bitmap.open(calibBitmapsFile[calibrationStep + 1]) - end - lcd.drawBitmap(calibBitmaps[calibrationStep + 1], 200, 70) - for index = 1, 3, 1 do - local field = fields[index] - lcd.drawText(70, 80+20*index, field[1]..":", TEXT_COLOR) - lcd.drawNumber(90, 80+20*index, field[4]/10, LEFT+PREC2) - end - - local attr = calibrationState == 0 and INVERS or 0 - lcd.drawText(160, 220, "Press [Enter] when ready", attr) - else - lcd.drawText(160, 50, "Calibration completed", 0) - lcd.drawBitmap(Bitmap.open("img/done.bmp"),200, 100) - lcd.drawText(160, 220, "Press [RTN] when ready", attr) - end - if calibrationStep > 6 and (event == EVT_ENTER_BREAK or event == EVT_EXIT_BREAK) then - return 2 - elseif event == EVT_ENTER_BREAK then - calibrationState = 1 - elseif event == EVT_EXIT_BREAK then - if calibrationStep > 0 then - calibrationStep = 0 - end - end - return 0 - -end - --- Init -local function init() - current, edit, refreshState, refreshIndex = 1, false, 0, 0 - pages = { - -- runConfigPage, - -- runSettingsPage, - runCalibrationPage - } -end - --- Main -local function run(event) - if event == nil then - error("Cannot be run as a model script!") - return 2 - elseif event == EVT_PAGE_BREAK or event == EVT_PAGEDN_FIRST then - selectPage(1) - elseif event == EVT_PAGE_LONG or event == EVT_PAGEUP_FIRST then - killEvents(event); - selectPage(-1) - end - - local result = pages[page](event) - refreshNext() - - return result -end - -return { init=init, run=run } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/S6R/S6R.lua opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/S6R/S6R.lua --- opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/S6R/S6R.lua 2017-05-14 17:18:57.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/S6R/S6R.lua 1970-01-01 00:00:00.000000000 +0000 @@ -1,296 +0,0 @@ -local VALUE = 0 -local COMBO = 1 - -local COLUMN_2 = 300 - -local edit = false -local page = 1 -local current = 1 -local refreshState = 0 -local refreshIndex = 0 -local calibrationState = 0 -local pageOffset = 0 -local calibrationStep = 0 -local pages = {} -local fields = {} -local modifications = {} -local wingBitmaps = {} -local mountBitmaps = {} - -local configFields = { - {"Wing type:", COMBO, 0x80, nil, { "Normal", "Delta", "VTail" } }, - {"Mounting type:", COMBO, 0x81, nil, { "Horz", "Horz rev.", "Vert", "Vert rev." } }, -} -local wingBitmapsFile = {"img/plane_b.png", "img/delta_b.png", "img/planev_b.png"} -local mountBitmapsFile = {"img/up.png", "img/down.png", "img/vert.png", "img/vert-r.png"} - -local settingsFields = { - {"S6R functions:", COMBO, 0x9C, nil, { "Disable", "Enable" } }, - {"CH5 mode:", COMBO, 0xA8, nil, { "AIL2", "AUX1" } }, - {"CH6 mode:", COMBO, 0xA9, nil, { "ELE2", "AUX2" } }, - {"AIL direction:", COMBO, 0x82, nil, { "Normal", "Invers" }, { 255, 0 } }, - {"ELE direction:", COMBO, 0x83, nil, { "Normal", "Invers" }, { 255, 0 } }, - {"RUD direction:", COMBO, 0x84, nil, { "Normal", "Invers" }, { 255, 0 } }, - {"AIL2 direction:", COMBO, 0x9A, nil, { "Normal", "Invers" }, { 255, 0 } }, - {"ELE2 direction:", COMBO, 0x9B, nil, { "Normal", "Invers" }, { 255, 0 } }, - {"AIL stabilize gain:", VALUE, 0x85, nil, 0, 200, "%"}, - {"ELE stabilize gain:", VALUE, 0x86, nil, 0, 200, "%"}, - {"RUD stabilize gain:", VALUE, 0x87, nil, 0, 200, "%"}, - {"AIL auto level gain:", VALUE, 0x88, nil, 0, 200, "%"}, - {"ELE auto level gain:", VALUE, 0x89, nil, 0, 200, "%"}, - {"ELE upright gain:", VALUE, 0x8C, nil, 0, 200, "%"}, - {"RUD upright gain:", VALUE, 0x8D, nil, 0, 200, "%"}, - {"AIL crab gain:", VALUE, 0x8E, nil, 0, 200, "%"}, - {"RUD crab gain:", VALUE, 0x90, nil, 0, 200, "%"}, - {"AIL auto angle offset:", VALUE, 0x91, nil, -20, 20, "%", 0x6C}, - {"ELE auto angle offset:", VALUE, 0x92, nil, -20, 20, "%", 0x6C}, - {"ELE upright angle offset:", VALUE, 0x95, nil, -20, 20, "%", 0x6C}, - {"RUD upright angle offset:", VALUE, 0x96, nil, -20, 20, "%", 0x6C}, - {"AIL crab angle offset:", VALUE, 0x97, nil, -20, 20, "%", 0x6C}, - {"RUD crab angle offset:", VALUE, 0x99, nil, -20, 20, "%", 0x6C}, -} - -local calibrationFields = { - {"X:", VALUE, 0x9E, 0, -100, 100, "%"}, - {"Y:", VALUE, 0x9F, 0, -100, 100, "%"}, - {"Z:", VALUE, 0xA0, 0, -100, 100, "%"} -} - -local function drawScreenTitle(title,page, pages) - lcd.drawFilledRectangle(0, 0, LCD_W, 30, TITLE_BGCOLOR) - lcd.drawText(1, 5, title, MENU_TITLE_COLOR) - lcd.drawText(LCD_W-40, 5, page.."/"..pages, MENU_TITLE_COLOR) -end - --- Change display attribute to current field -local function addField(step) - local field = fields[current] - local min, max - if field[2] == VALUE then - min = field[5] - max = field[6] - elseif field[2] == COMBO then - min = 0 - max = #(field[5]) - 1 - end - if (step < 0 and field[4] > min) or (step > 0 and field[4] < max) then - field[4] = field[4] + step - end -end - --- Select the next or previous page -local function selectPage(step) - page = 1 + ((page + step - 1 + #pages) % #pages) - refreshIndex = 0 - calibrationStep = 0 - pageOffset = 0 -end - --- Select the next or previous editable field -local function selectField(step) - current = 1 + ((current + step - 1 + #fields) % #fields) - if current > 7 + pageOffset then - pageOffset = current - 7 - elseif current <= pageOffset then - pageOffset = current - 1 - end -end - -local function drawProgressBar() - local width = (300 * refreshIndex) / #fields - lcd.drawRectangle(100, 10, 300, 6) - lcd.drawFilledRectangle(102, 13, width, 2); -end - --- Redraw the current page -local function redrawFieldsPage(event) - lcd.clear() - drawScreenTitle("S6R", page, #pages) - - if refreshIndex < #fields then - drawProgressBar() - end - - for index = 1, 10, 1 do - local field = fields[pageOffset+index] - if field == nil then - break - end - - local attr = current == (pageOffset+index) and ((edit == true and BLINK or 0) + INVERS) or 0 - attr = attr + TEXT_COLOR - - lcd.drawText(1, 30+20*index, field[1], TEXT_COLOR) - - if field[4] == nil then - lcd.drawText(COLUMN_2, 30+20*index, "---", attr) - else - if field[2] == VALUE then - lcd.drawNumber(COLUMN_2, 30+20*index, field[4], LEFT + attr) - elseif field[2] == COMBO then - if field[4] >= 0 and field[4] < #(field[5]) then - lcd.drawText(COLUMN_2, 30+20*index, field[5][1+field[4]], attr) - end - end - end - end -end - -local function telemetryRead(field) - return sportTelemetryPush(0x17, 0x30, 0x0C30, field) -end - -local function telemetryWrite(field, value) - return sportTelemetryPush(0x17, 0x31, 0x0C30, field + value*256) -end - -local telemetryPopTimeout = 0 -local function refreshNext() - if refreshState == 0 then - if calibrationState == 1 then - if telemetryWrite(0x9D, calibrationStep) == true then - refreshState = 1 - calibrationState = 2 - telemetryPopTimeout = getTime() + 80 -- normal delay is 500ms - end - elseif #modifications > 0 then - telemetryWrite(modifications[1][1], modifications[1][2]) - modifications[1] = nil - elseif refreshIndex < #fields then - local field = fields[refreshIndex + 1] - if telemetryRead(field[3]) == true then - refreshState = 1 - telemetryPopTimeout = getTime() + 80 -- normal delay is 500ms - end - end - elseif refreshState == 1 then - local physicalId, primId, dataId, value = sportTelemetryPop() - if physicalId == 0x1A and primId == 0x32 and dataId == 0x0C30 then - local fieldId = value % 256 - if calibrationState == 2 then - if fieldId == 0x9D then - refreshState = 0 - calibrationState = 0 - calibrationStep = (calibrationStep + 1) % 7 - end - else - local field = fields[refreshIndex + 1] - if fieldId == field[3] then - local value = math.floor(value / 256) - if field[3] >= 0x9E and field[3] <= 0xA0 then - local b1 = value % 256 - local b2 = math.floor(value / 256) - value = b1*256 + b2 - value = value - bit32.band(value, 0x8000) * 2 - end - if field[2] == COMBO and #field == 6 then - for index = 1, #(field[6]), 1 do - if value == field[6][index] then - value = index - 1 - break - end - end - elseif field[2] == VALUE and #field == 8 then - value = value - field[8] + field[5] - end - fields[refreshIndex + 1][4] = value - refreshIndex = refreshIndex + 1 - refreshState = 0 - end - end - elseif getTime() > telemetryPopTimeout then - refreshState = 0 - calibrationState = 0 - end - end -end - -local function updateField(field) - local value = field[4] - if field[2] == COMBO and #field == 6 then - value = field[6][1+value] - elseif field[2] == VALUE and #field == 8 then - value = value + field[8] - field[5] - end - modifications[#modifications+1] = { field[3], value } -end - --- Main -local function runFieldsPage(event) - if event == EVT_EXIT_BREAK then -- exit script - return 2 - elseif event == EVT_ENTER_BREAK or event == EVT_ROT_BREAK then -- toggle editing/selecting current field - if fields[current][4] ~= nil then - edit = not edit - if edit == false then - updateField(fields[current]) - end - end - elseif edit then - if event == EVT_PLUS_FIRST or event == EVT_ROT_RIGHT or event == EVT_PLUS_REPT then - addField(1) - elseif event == EVT_MINUS_FIRST or event == EVT_ROT_LEFT or event == EVT_MINUS_REPT then - addField(-1) - end - else - if event == EVT_MINUS_FIRST or event == EVT_ROT_RIGHT then - selectField(1) - elseif event == EVT_PLUS_FIRST or event == EVT_ROT_LEFT then - selectField(-1) - end - end - redrawFieldsPage(event) - return 0 -end - -local function runConfigPage(event) - fields = configFields - local result = runFieldsPage(event) - if fields[1][4] ~= nil then - if wingBitmaps[1 + fields[1][4]] == nil then - wingBitmaps[1 + fields[1][4]] = Bitmap.open(wingBitmapsFile[1 + fields[1][4]]) - end - lcd.drawBitmap(wingBitmaps[1 + fields[1][4]], 10, 90) - end - if fields[2][4] ~= nil then - if mountBitmaps[1 + fields[2][4]] == nil then - mountBitmaps[1 + fields[2][4]] = Bitmap.open(mountBitmapsFile[1 + fields[2][4]]) - end - lcd.drawBitmap(mountBitmaps[1 + fields[2][4]], 190, 110) - end - return result -end - -local function runSettingsPage(event) - fields = settingsFields - return runFieldsPage(event) -end - --- Init -local function init() - current, edit, refreshState, refreshIndex = 1, false, 0, 0 - pages = { - runConfigPage, - runSettingsPage, - } -end - --- Main -local function run(event) - if event == nil then - error("Cannot be run as a model script!") - return 2 - elseif event == EVT_PAGE_BREAK or event == EVT_PAGEDN_FIRST then - selectPage(1) - elseif event == EVT_PAGE_LONG or event == EVT_PAGEUP_FIRST then - killEvents(event); - selectPage(-1) - end - - local result = pages[page](event) - refreshNext() - - return result -end - -return { init=init, run=run } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/SCRIPTS/TEMPLATES/readme.txt opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/SCRIPTS/TEMPLATES/readme.txt --- opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/SCRIPTS/TEMPLATES/readme.txt 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/SCRIPTS/TEMPLATES/readme.txt 1970-01-01 00:00:00.000000000 +0000 @@ -1 +0,0 @@ -This directory is for template lua scripts. diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/SCRIPTS/WIZARD/plane/wizard.lua opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/SCRIPTS/WIZARD/plane/wizard.lua --- opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/SCRIPTS/WIZARD/plane/wizard.lua 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/SCRIPTS/WIZARD/plane/wizard.lua 2017-12-17 16:22:27.000000000 +0000 @@ -1,3 +1,19 @@ +---- ######################################################################### +---- # # +---- # Copyright (C) OpenTX # +-----# # +---- # License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html # +---- # # +---- # This program is free software; you can redistribute it and/or modify # +---- # it under the terms of the GNU General Public License version 2 as # +---- # published by the Free Software Foundation. # +---- # # +---- # 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. # +---- # # +---- ######################################################################### local VALUE = 0 local COMBO = 1 @@ -406,15 +422,15 @@ if(AilFields[1][5] == 1) then addMix(AilFields[2][5], MIXSRC_FIRST_INPUT+defaultChannel(3), "Ail") elseif (AilFields[1][5] == 2) then - addMix(AilFields[2][5], MIXSRC_FIRST_INPUT+defaultChannel(3), "Ail1") - addMix(AilFields[3][5], MIXSRC_FIRST_INPUT+defaultChannel(3), "Ail2", -100) + addMix(AilFields[2][5], MIXSRC_FIRST_INPUT+defaultChannel(3), "AilL") + addMix(AilFields[3][5], MIXSRC_FIRST_INPUT+defaultChannel(3), "AilR", -100) end -- Flaps if(FlapsFields[1][5] == 1) then addMix(FlapsFields[2][5], MIXSRC_SA, "Flaps") elseif (FlapsFields[1][5] == 2) then - addMix(FlapsFields[2][5], MIXSRC_SA, "Flaps1") - addMix(FlapsFields[3][5], MIXSRC_SA, "Flaps2") + addMix(FlapsFields[2][5], MIXSRC_SA, "FlapsL") + addMix(FlapsFields[3][5], MIXSRC_SA, "FlapsR") end -- Tail if(TailFields[1][5] == 0) then @@ -423,14 +439,14 @@ addMix(TailFields[2][5], MIXSRC_FIRST_INPUT+defaultChannel(1), "Elev") addMix(TailFields[3][5], MIXSRC_FIRST_INPUT+defaultChannel(0), "Rudder") elseif (TailFields[1][5] == 2) then - addMix(TailFields[2][5], MIXSRC_FIRST_INPUT+defaultChannel(1), "Elev1") + addMix(TailFields[2][5], MIXSRC_FIRST_INPUT+defaultChannel(1), "ElevL") addMix(TailFields[3][5], MIXSRC_FIRST_INPUT+defaultChannel(0), "Rudder") - addMix(TailFields[4][5], MIXSRC_FIRST_INPUT+defaultChannel(1), "Elev2") + addMix(TailFields[4][5], MIXSRC_FIRST_INPUT+defaultChannel(1), "ElevR") elseif (TailFields[1][5] == 3) then - addMix(TailFields[2][5], MIXSRC_FIRST_INPUT+defaultChannel(1), "VTailE", 50) - addMix(TailFields[2][5], MIXSRC_FIRST_INPUT+defaultChannel(0), "VTailR", 50, 1) - addMix(TailFields[3][5], MIXSRC_FIRST_INPUT+defaultChannel(1), "VTailE", 50) - addMix(TailFields[3][5], MIXSRC_FIRST_INPUT+defaultChannel(0), "VTailR", -50, 1) + addMix(TailFields[2][5], MIXSRC_FIRST_INPUT+defaultChannel(1), "V-EleL", 50) + addMix(TailFields[2][5], MIXSRC_FIRST_INPUT+defaultChannel(0), "V-RudL", 50, 1) + addMix(TailFields[3][5], MIXSRC_FIRST_INPUT+defaultChannel(1), "V-EleR", 50) + addMix(TailFields[3][5], MIXSRC_FIRST_INPUT+defaultChannel(0), "V-RudR", -50, 1) end lcd.drawText(70, 90, "Model successfully created !", TEXT_COLOR) lcd.drawText(100, 130, "Press RTN to exit", TEXT_COLOR) Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/SxR/img/back.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/SxR/img/back.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/SxR/img/delta_b.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/SxR/img/delta_b.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/SxR/img/done.bmp and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/SxR/img/done.bmp differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/SxR/img/down.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/SxR/img/down.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/SxR/img/forward.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/SxR/img/forward.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/SxR/img/left.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/SxR/img/left.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/SxR/img/plane_b.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/SxR/img/plane_b.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/SxR/img/planev_b.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/SxR/img/planev_b.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/SxR/img/planev_s.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/SxR/img/planev_s.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/SxR/img/right.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/SxR/img/right.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/SxR/img/up.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/SxR/img/up.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/SxR/img/vert.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/SxR/img/vert.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/SxR/img/vert-r.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/SxR/img/vert-r.png differ diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/SxR/SxR_Calibrate.lua opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/SxR/SxR_Calibrate.lua --- opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/SxR/SxR_Calibrate.lua 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/SxR/SxR_Calibrate.lua 2017-11-11 11:29:14.000000000 +0000 @@ -0,0 +1,356 @@ +---- ######################################################################### +---- # # +---- # Copyright (C) OpenTX # +-----# # +---- # License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html # +---- # # +---- # This program is free software; you can redistribute it and/or modify # +---- # it under the terms of the GNU General Public License version 2 as # +---- # published by the Free Software Foundation. # +---- # # +---- # 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. # +---- # # +---- ######################################################################### +local VALUE = 0 +local COMBO = 1 + +local COLUMN_2 = 300 + +local edit = false +local page = 1 +local current = 1 +local refreshState = 0 +local refreshIndex = 0 +local calibrationState = 0 +local pageOffset = 0 +local calibrationStep = 0 +local pages = {} +local fields = {} +local modifications = {} +local wingBitmaps = {} +local mountBitmaps = {} +local calibBitmaps = {} + +local configFields = { + {"Wing type:", COMBO, 0x80, nil, { "Normal", "Delta", "VTail" } }, + {"Mounting type:", COMBO, 0x81, nil, { "Horz", "Horz rev.", "Vert", "Vert rev." } }, +} +local calibrationPositions = { "up", "down", "left", "right", "forward", "back" } +local wingBitmapsFile = {"img/plane_b.png", "img/delta_b.png", "img/planev_b.png"} +local mountBitmapsFile = {"img/up.png", "img/down.png", "img/vert.png", "img/vert-r.png"} +local calibBitmapsFile = {"img/up.png", "img/down.png", "img/left.png", "img/right.png", "img/forward.png", "img/back.png"} + +local settingsFields = { + {"SxR functions:", COMBO, 0x9C, nil, { "Disable", "Enable" } }, + {"CH5 mode:", COMBO, 0xA8, nil, { "AIL2", "AUX1" } }, + {"CH6 mode:", COMBO, 0xA9, nil, { "ELE2", "AUX2" } }, + {"AIL direction:", COMBO, 0x82, nil, { "Normal", "Invers" }, { 255, 0 } }, + {"ELE direction:", COMBO, 0x83, nil, { "Normal", "Invers" }, { 255, 0 } }, + {"RUD direction:", COMBO, 0x84, nil, { "Normal", "Invers" }, { 255, 0 } }, + {"AIL2 direction:", COMBO, 0x9A, nil, { "Normal", "Invers" }, { 255, 0 } }, + {"ELE2 direction:", COMBO, 0x9B, nil, { "Normal", "Invers" }, { 255, 0 } }, + {"AIL stabilize gain:", VALUE, 0x85, nil, 0, 200, "%"}, + {"ELE stabilize gain:", VALUE, 0x86, nil, 0, 200, "%"}, + {"RUD stabilize gain:", VALUE, 0x87, nil, 0, 200, "%"}, + {"AIL auto level gain:", VALUE, 0x88, nil, 0, 200, "%"}, + {"ELE auto level gain:", VALUE, 0x89, nil, 0, 200, "%"}, + {"ELE upright gain:", VALUE, 0x8C, nil, 0, 200, "%"}, + {"RUD upright gain:", VALUE, 0x8D, nil, 0, 200, "%"}, + {"AIL crab gain:", VALUE, 0x8E, nil, 0, 200, "%"}, + {"RUD crab gain:", VALUE, 0x90, nil, 0, 200, "%"}, + {"AIL auto angle offset:", VALUE, 0x91, nil, -20, 20, "%", 0x6C}, + {"ELE auto angle offset:", VALUE, 0x92, nil, -20, 20, "%", 0x6C}, + {"ELE upright angle offset:", VALUE, 0x95, nil, -20, 20, "%", 0x6C}, + {"RUD upright angle offset:", VALUE, 0x96, nil, -20, 20, "%", 0x6C}, + {"AIL crab angle offset:", VALUE, 0x97, nil, -20, 20, "%", 0x6C}, + {"RUD crab angle offset:", VALUE, 0x99, nil, -20, 20, "%", 0x6C}, +} + +local calibrationFields = { + {"X:", VALUE, 0x9E, 0, -100, 100, "%"}, + {"Y:", VALUE, 0x9F, 0, -100, 100, "%"}, + {"Z:", VALUE, 0xA0, 0, -100, 100, "%"} +} + +local function drawScreenTitle(title,page, pages) + lcd.drawFilledRectangle(0, 0, LCD_W, 30, TITLE_BGCOLOR) + lcd.drawText(1, 5, title, MENU_TITLE_COLOR) + lcd.drawText(LCD_W-40, 5, page.."/"..pages, MENU_TITLE_COLOR) +end + +-- Change display attribute to current field +local function addField(step) + local field = fields[current] + local min, max + if field[2] == VALUE then + min = field[5] + max = field[6] + elseif field[2] == COMBO then + min = 0 + max = #(field[5]) - 1 + end + if (step < 0 and field[4] > min) or (step > 0 and field[4] < max) then + field[4] = field[4] + step + end +end + +-- Select the next or previous page +local function selectPage(step) + page = 1 + ((page + step - 1 + #pages) % #pages) + refreshIndex = 0 + calibrationStep = 0 + pageOffset = 0 +end + +-- Select the next or previous editable field +local function selectField(step) + current = 1 + ((current + step - 1 + #fields) % #fields) + if current > 7 + pageOffset then + pageOffset = current - 7 + elseif current <= pageOffset then + pageOffset = current - 1 + end +end + +local function drawProgressBar() + local width = (300 * refreshIndex) / #fields + lcd.drawRectangle(100, 10, 300, 6) + lcd.drawFilledRectangle(102, 13, width, 2); +end + +-- Redraw the current page +local function redrawFieldsPage(event) + lcd.clear() + drawScreenTitle("SxR", page, #pages) + + if refreshIndex < #fields then + drawProgressBar() + end + + for index = 1, 10, 1 do + local field = fields[pageOffset+index] + if field == nil then + break + end + + local attr = current == (pageOffset+index) and ((edit == true and BLINK or 0) + INVERS) or 0 + attr = attr + TEXT_COLOR + + lcd.drawText(1, 30+20*index, field[1], TEXT_COLOR) + + if field[4] == nil then + lcd.drawText(COLUMN_2, 30+20*index, "---", attr) + else + if field[2] == VALUE then + lcd.drawNumber(COLUMN_2, 30+20*index, field[4], LEFT + attr) + elseif field[2] == COMBO then + if field[4] >= 0 and field[4] < #(field[5]) then + lcd.drawText(COLUMN_2, 30+20*index, field[5][1+field[4]], attr) + end + end + end + end +end + +local function telemetryRead(field) + return sportTelemetryPush(0x17, 0x30, 0x0C30, field) +end + +local function telemetryWrite(field, value) + return sportTelemetryPush(0x17, 0x31, 0x0C30, field + value*256) +end + +local telemetryPopTimeout = 0 +local function refreshNext() + if refreshState == 0 then + if calibrationState == 1 then + if telemetryWrite(0x9D, calibrationStep) == true then + refreshState = 1 + calibrationState = 2 + telemetryPopTimeout = getTime() + 80 -- normal delay is 500ms + end + elseif #modifications > 0 then + telemetryWrite(modifications[1][1], modifications[1][2]) + modifications[1] = nil + elseif refreshIndex < #fields then + local field = fields[refreshIndex + 1] + if telemetryRead(field[3]) == true then + refreshState = 1 + telemetryPopTimeout = getTime() + 80 -- normal delay is 500ms + end + end + elseif refreshState == 1 then + local physicalId, primId, dataId, value = sportTelemetryPop() + if physicalId == 0x1A and primId == 0x32 and dataId == 0x0C30 then + local fieldId = value % 256 + if calibrationState == 2 then + if fieldId == 0x9D then + refreshState = 0 + calibrationState = 0 + calibrationStep = (calibrationStep + 1) % 7 + end + else + local field = fields[refreshIndex + 1] + if fieldId == field[3] then + local value = math.floor(value / 256) + if field[3] >= 0x9E and field[3] <= 0xA0 then + local b1 = value % 256 + local b2 = math.floor(value / 256) + value = b1*256 + b2 + value = value - bit32.band(value, 0x8000) * 2 + end + if field[2] == COMBO and #field == 6 then + for index = 1, #(field[6]), 1 do + if value == field[6][index] then + value = index - 1 + break + end + end + elseif field[2] == VALUE and #field == 8 then + value = value - field[8] + field[5] + end + fields[refreshIndex + 1][4] = value + refreshIndex = refreshIndex + 1 + refreshState = 0 + end + end + elseif getTime() > telemetryPopTimeout then + refreshState = 0 + calibrationState = 0 + end + end +end + +local function updateField(field) + local value = field[4] + if field[2] == COMBO and #field == 6 then + value = field[6][1+value] + elseif field[2] == VALUE and #field == 8 then + value = value + field[8] - field[5] + end + modifications[#modifications+1] = { field[3], value } +end + +-- Main +local function runFieldsPage(event) + if event == EVT_EXIT_BREAK then -- exit script + return 2 + elseif event == EVT_ENTER_BREAK or event == EVT_ROT_BREAK then -- toggle editing/selecting current field + if fields[current][4] ~= nil then + edit = not edit + if edit == false then + updateField(fields[current]) + end + end + elseif edit then + if event == EVT_PLUS_FIRST or event == EVT_ROT_RIGHT or event == EVT_PLUS_REPT then + addField(1) + elseif event == EVT_MINUS_FIRST or event == EVT_ROT_LEFT or event == EVT_MINUS_REPT then + addField(-1) + end + else + if event == EVT_MINUS_FIRST or event == EVT_ROT_RIGHT then + selectField(1) + elseif event == EVT_PLUS_FIRST or event == EVT_ROT_LEFT then + selectField(-1) + end + end + redrawFieldsPage(event) + return 0 +end + +local function runConfigPage(event) + fields = configFields + local result = runFieldsPage(event) + if fields[1][4] ~= nil then + if wingBitmaps[1 + fields[1][4]] == nil then + wingBitmaps[1 + fields[1][4]] = Bitmap.open(wingBitmapsFile[1 + fields[1][4]]) + end + lcd.drawBitmap(wingBitmaps[1 + fields[1][4]], 10, 90) + end + if fields[2][4] ~= nil then + if mountBitmaps[1 + fields[2][4]] == nil then + mountBitmaps[1 + fields[2][4]] = Bitmap.open(mountBitmapsFile[1 + fields[2][4]]) + end + lcd.drawBitmap(mountBitmaps[1 + fields[2][4]], 190, 110) + end + return result +end + +local function runSettingsPage(event) + fields = settingsFields + return runFieldsPage(event) +end + +local function runCalibrationPage(event) + fields = calibrationFields + if refreshIndex == #fields then + refreshIndex = 0 + end + lcd.clear() + drawScreenTitle("SxR", page, #pages) + if(calibrationStep < 6) then + local position = calibrationPositions[1 + calibrationStep] + lcd.drawText(100, 50, "Place the SxR in the following position", TEXT_COLOR) + if calibBitmaps[calibrationStep + 1] == nil then + calibBitmaps[calibrationStep + 1] = Bitmap.open(calibBitmapsFile[calibrationStep + 1]) + end + lcd.drawBitmap(calibBitmaps[calibrationStep + 1], 200, 70) + for index = 1, 3, 1 do + local field = fields[index] + lcd.drawText(70, 80+20*index, field[1]..":", TEXT_COLOR) + lcd.drawNumber(90, 80+20*index, field[4]/10, LEFT+PREC2) + end + + local attr = calibrationState == 0 and INVERS or 0 + lcd.drawText(160, 220, "Press [Enter] when ready", attr) + else + lcd.drawText(160, 50, "Calibration completed", 0) + lcd.drawBitmap(Bitmap.open("img/done.bmp"),200, 100) + lcd.drawText(160, 220, "Press [RTN] when ready", attr) + end + if calibrationStep > 6 and (event == EVT_ENTER_BREAK or event == EVT_EXIT_BREAK) then + return 2 + elseif event == EVT_ENTER_BREAK then + calibrationState = 1 + elseif event == EVT_EXIT_BREAK then + if calibrationStep > 0 then + calibrationStep = 0 + end + end + return 0 + +end + +-- Init +local function init() + current, edit, refreshState, refreshIndex = 1, false, 0, 0 + pages = { + -- runConfigPage, + -- runSettingsPage, + runCalibrationPage + } +end + +-- Main +local function run(event) + if event == nil then + error("Cannot be run as a model script!") + return 2 + elseif event == EVT_PAGE_BREAK or event == EVT_PAGEDN_FIRST then + selectPage(1) + elseif event == EVT_PAGE_LONG or event == EVT_PAGEUP_FIRST then + killEvents(event); + selectPage(-1) + end + + local result = pages[page](event) + refreshNext() + + return result +end + +return { init=init, run=run } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/SxR/SxR.lua opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/SxR/SxR.lua --- opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/SxR/SxR.lua 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/SxR/SxR.lua 2017-11-11 11:29:14.000000000 +0000 @@ -0,0 +1,315 @@ +---- ######################################################################### +---- # # +---- # Copyright (C) OpenTX # +-----# # +---- # License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html # +---- # # +---- # This program is free software; you can redistribute it and/or modify # +---- # it under the terms of the GNU General Public License version 2 as # +---- # published by the Free Software Foundation. # +---- # # +---- # 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. # +---- # # +---- ######################################################################### +local VALUE = 0 +local COMBO = 1 + +local COLUMN_2 = 300 + +local edit = false +local page = 1 +local current = 1 +local refreshState = 0 +local refreshIndex = 0 +local calibrationState = 0 +local pageOffset = 0 +local calibrationStep = 0 +local pages = {} +local fields = {} +local modifications = {} +local wingBitmaps = {} +local mountBitmaps = {} + +local configFields = { + {"Wing type:", COMBO, 0x80, nil, { "Normal", "Delta", "VTail" } }, + {"Mounting type:", COMBO, 0x81, nil, { "Horz", "Horz rev.", "Vert", "Vert rev." } }, +} +local wingBitmapsFile = {"img/plane_b.png", "img/delta_b.png", "img/planev_b.png"} +local mountBitmapsFile = {"img/up.png", "img/down.png", "img/vert.png", "img/vert-r.png"} + +local settingsFields = { + {"SxR functions:", COMBO, 0x9C, nil, { "Disable", "Enable" } }, + {"Quick Mode:", COMBO, 0xAA, nil, { "Disable", "Enable" } }, + {"CH5 mode:", COMBO, 0xA8, nil, { "AIL2", "AUX1" } }, + {"CH6 mode:", COMBO, 0xA9, nil, { "ELE2", "AUX2" } }, + {"AIL direction:", COMBO, 0x82, nil, { "Normal", "Invers" }, { 255, 0 } }, + {"ELE direction:", COMBO, 0x83, nil, { "Normal", "Invers" }, { 255, 0 } }, + {"RUD direction:", COMBO, 0x84, nil, { "Normal", "Invers" }, { 255, 0 } }, + {"AIL2 direction:", COMBO, 0x9A, nil, { "Normal", "Invers" }, { 255, 0 } }, + {"ELE2 direction:", COMBO, 0x9B, nil, { "Normal", "Invers" }, { 255, 0 } }, + {"AIL stabilize gain:", VALUE, 0x85, nil, 0, 200, "%"}, + {"ELE stabilize gain:", VALUE, 0x86, nil, 0, 200, "%"}, + {"RUD stabilize gain:", VALUE, 0x87, nil, 0, 200, "%"}, + {"AIL auto level gain:", VALUE, 0x88, nil, 0, 200, "%"}, + {"ELE auto level gain:", VALUE, 0x89, nil, 0, 200, "%"}, + {"ELE upright gain:", VALUE, 0x8C, nil, 0, 200, "%"}, + {"RUD upright gain:", VALUE, 0x8D, nil, 0, 200, "%"}, + {"AIL crab gain:", VALUE, 0x8E, nil, 0, 200, "%"}, + {"RUD crab gain:", VALUE, 0x90, nil, 0, 200, "%"}, + {"AIL auto angle offset:", VALUE, 0x91, nil, -20, 20, "%", 0x6C}, + {"ELE auto angle offset:", VALUE, 0x92, nil, -20, 20, "%", 0x6C}, + {"ELE upright angle offset:", VALUE, 0x95, nil, -20, 20, "%", 0x6C}, + {"RUD upright angle offset:", VALUE, 0x96, nil, -20, 20, "%", 0x6C}, + {"AIL crab angle offset:", VALUE, 0x97, nil, -20, 20, "%", 0x6C}, + {"RUD crab angle offset:", VALUE, 0x99, nil, -20, 20, "%", 0x6C}, +} + +local calibrationFields = { + {"X:", VALUE, 0x9E, 0, -100, 100, "%"}, + {"Y:", VALUE, 0x9F, 0, -100, 100, "%"}, + {"Z:", VALUE, 0xA0, 0, -100, 100, "%"} +} + +local function drawScreenTitle(title,page, pages) + lcd.drawFilledRectangle(0, 0, LCD_W, 30, TITLE_BGCOLOR) + lcd.drawText(1, 5, title, MENU_TITLE_COLOR) + lcd.drawText(LCD_W-40, 5, page.."/"..pages, MENU_TITLE_COLOR) +end + +-- Change display attribute to current field +local function addField(step) + local field = fields[current] + local min, max + if field[2] == VALUE then + min = field[5] + max = field[6] + elseif field[2] == COMBO then + min = 0 + max = #(field[5]) - 1 + end + if (step < 0 and field[4] > min) or (step > 0 and field[4] < max) then + field[4] = field[4] + step + end +end + +-- Select the next or previous page +local function selectPage(step) + page = 1 + ((page + step - 1 + #pages) % #pages) + refreshIndex = 0 + calibrationStep = 0 + pageOffset = 0 +end + +-- Select the next or previous editable field +local function selectField(step) + current = 1 + ((current + step - 1 + #fields) % #fields) + if current > 7 + pageOffset then + pageOffset = current - 7 + elseif current <= pageOffset then + pageOffset = current - 1 + end +end + +local function drawProgressBar() + local width = (300 * refreshIndex) / #fields + lcd.drawRectangle(100, 10, 300, 6) + lcd.drawFilledRectangle(102, 13, width, 2); +end + +-- Redraw the current page +local function redrawFieldsPage(event) + lcd.clear() + drawScreenTitle("SxR", page, #pages) + + if refreshIndex < #fields then + drawProgressBar() + end + + for index = 1, 10, 1 do + local field = fields[pageOffset+index] + if field == nil then + break + end + + local attr = current == (pageOffset+index) and ((edit == true and BLINK or 0) + INVERS) or 0 + attr = attr + TEXT_COLOR + + lcd.drawText(1, 30+20*index, field[1], TEXT_COLOR) + + if field[4] == nil then + lcd.drawText(COLUMN_2, 30+20*index, "---", attr) + else + if field[2] == VALUE then + lcd.drawNumber(COLUMN_2, 30+20*index, field[4], LEFT + attr) + elseif field[2] == COMBO then + if field[4] >= 0 and field[4] < #(field[5]) then + lcd.drawText(COLUMN_2, 30+20*index, field[5][1+field[4]], attr) + end + end + end + end +end + +local function telemetryRead(field) + return sportTelemetryPush(0x17, 0x30, 0x0C30, field) +end + +local function telemetryWrite(field, value) + return sportTelemetryPush(0x17, 0x31, 0x0C30, field + value*256) +end + +local telemetryPopTimeout = 0 +local function refreshNext() + if refreshState == 0 then + if calibrationState == 1 then + if telemetryWrite(0x9D, calibrationStep) == true then + refreshState = 1 + calibrationState = 2 + telemetryPopTimeout = getTime() + 120 -- normal delay is 500ms + end + elseif #modifications > 0 then + telemetryWrite(modifications[1][1], modifications[1][2]) + modifications[1] = nil + elseif refreshIndex < #fields then + local field = fields[refreshIndex + 1] + if telemetryRead(field[3]) == true then + refreshState = 1 + telemetryPopTimeout = getTime() + 80 -- normal delay is 500ms + end + end + elseif refreshState == 1 then + local physicalId, primId, dataId, value = sportTelemetryPop() + if physicalId == 0x1A and primId == 0x32 and dataId == 0x0C30 then + local fieldId = value % 256 + if calibrationState == 2 then + if fieldId == 0x9D then + refreshState = 0 + calibrationState = 0 + calibrationStep = (calibrationStep + 1) % 7 + end + else + local field = fields[refreshIndex + 1] + if fieldId == field[3] then + local value = math.floor(value / 256) + if field[3] >= 0x9E and field[3] <= 0xA0 then + local b1 = value % 256 + local b2 = math.floor(value / 256) + value = b1*256 + b2 + value = value - bit32.band(value, 0x8000) * 2 + end + if field[2] == COMBO and #field == 6 then + for index = 1, #(field[6]), 1 do + if value == field[6][index] then + value = index - 1 + break + end + end + elseif field[2] == VALUE and #field == 8 then + value = value - field[8] + field[5] + end + fields[refreshIndex + 1][4] = value + refreshIndex = refreshIndex + 1 + refreshState = 0 + end + end + elseif getTime() > telemetryPopTimeout then + fields[refreshIndex + 1][4] = nil + refreshIndex = refreshIndex + 1 + refreshState = 0 + calibrationState = 0 + end + end +end + +local function updateField(field) + local value = field[4] + if field[2] == COMBO and #field == 6 then + value = field[6][1+value] + elseif field[2] == VALUE and #field == 8 then + value = value + field[8] - field[5] + end + modifications[#modifications+1] = { field[3], value } +end + +-- Main +local function runFieldsPage(event) + if event == EVT_EXIT_BREAK then -- exit script + return 2 + elseif event == EVT_ENTER_BREAK or event == EVT_ROT_BREAK then -- toggle editing/selecting current field + if fields[current][4] ~= nil then + edit = not edit + if edit == false then + updateField(fields[current]) + end + end + elseif edit then + if event == EVT_PLUS_FIRST or event == EVT_ROT_RIGHT or event == EVT_PLUS_REPT then + addField(1) + elseif event == EVT_MINUS_FIRST or event == EVT_ROT_LEFT or event == EVT_MINUS_REPT then + addField(-1) + end + else + if event == EVT_MINUS_FIRST or event == EVT_ROT_RIGHT then + selectField(1) + elseif event == EVT_PLUS_FIRST or event == EVT_ROT_LEFT then + selectField(-1) + end + end + redrawFieldsPage(event) + return 0 +end + +local function runConfigPage(event) + fields = configFields + local result = runFieldsPage(event) + if fields[1][4] ~= nil then + if wingBitmaps[1 + fields[1][4]] == nil then + wingBitmaps[1 + fields[1][4]] = Bitmap.open(wingBitmapsFile[1 + fields[1][4]]) + end + lcd.drawBitmap(wingBitmaps[1 + fields[1][4]], 10, 90) + end + if fields[2][4] ~= nil then + if mountBitmaps[1 + fields[2][4]] == nil then + mountBitmaps[1 + fields[2][4]] = Bitmap.open(mountBitmapsFile[1 + fields[2][4]]) + end + lcd.drawBitmap(mountBitmaps[1 + fields[2][4]], 190, 110) + end + return result +end + +local function runSettingsPage(event) + fields = settingsFields + return runFieldsPage(event) +end + +-- Init +local function init() + current, edit, refreshState, refreshIndex = 1, false, 0, 0 + pages = { + runConfigPage, + runSettingsPage, + } +end + +-- Main +local function run(event) + if event == nil then + error("Cannot be run as a model script!") + return 2 + elseif event == EVT_PAGE_BREAK or event == EVT_PAGEDN_FIRST then + selectPage(1) + elseif event == EVT_PAGE_LONG or event == EVT_PAGEUP_FIRST then + killEvents(event); + selectPage(-1) + end + + local result = pages[page](event) + refreshNext() + + return result +end + +return { init=init, run=run } Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/THEMES/Darkblue/X10.bmp and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/THEMES/Darkblue/X10.bmp differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/THEMES/Darkblue/X10S.bmp and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/THEMES/Darkblue/X10S.bmp differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/THEMES/Default/X10.bmp and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/THEMES/Default/X10.bmp differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/THEMES/Default/X10S.bmp and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/THEMES/Default/X10S.bmp differ diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/WIDGETS/BattCheck/main.lua opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/WIDGETS/BattCheck/main.lua --- opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/WIDGETS/BattCheck/main.lua 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/WIDGETS/BattCheck/main.lua 2017-10-31 16:16:43.000000000 +0000 @@ -16,10 +16,12 @@ ---- # # ---- ######################################################################### +local shadowed = 0 local options = { { "Sensor", SOURCE, 1 }, - { "Color", COLOR, WHITE } + { "Color", COLOR, WHITE }, + { "Shadow", BOOL, 0 } } -- This function is runned once at the creation of the widget @@ -182,8 +184,8 @@ if type(mySensor) == "table" then local myString = string.format("%2.1fV", getCellSum(mySensor)).." ("..getCellCount(mySensor).."S)" local percent = getCellPercent(getCellAvg(mySensor)) - lcd.drawText(zone.zone.x + zone.zone.w, zone.zone.y + 22, myString, RIGHT + SMLSIZE + CUSTOM_COLOR) - lcd.drawText(zone.zone.x + zone.zone.w, zone.zone.y, percent.."%", RIGHT + MIDSIZE + CUSTOM_COLOR) + lcd.drawText(zone.zone.x + zone.zone.w, zone.zone.y + 22, myString, RIGHT + SMLSIZE + CUSTOM_COLOR + shadowed) + lcd.drawText(zone.zone.x + zone.zone.w, zone.zone.y, percent.."%", RIGHT + MIDSIZE + CUSTOM_COLOR + shadowed) -- fils batt lcd.setColor(CUSTOM_COLOR, getPercentColor(percent)) lcd.drawGauge(zone.zone.x+2, zone.zone.y+2, 75, zone.zone.h - 4, percent, 100, CUSTOM_COLOR) @@ -195,7 +197,7 @@ lcd.drawRectangle(zone.zone.x + myBatt.x + i, zone.zone.y + myBatt.y, myBatt.segments_w, myBatt.h, CUSTOM_COLOR, 1) end else - lcd.drawText(zone.zone.x, zone.zone.y+10, "No FLVSS sensor data", LEFT + SMLSIZE + INVERS + CUSTOM_COLOR) + lcd.drawText(zone.zone.x, zone.zone.y+10, "No FLVSS sensor data", LEFT + SMLSIZE + INVERS + CUSTOM_COLOR + shadowed) end return end @@ -208,7 +210,7 @@ lcd.setColor(CUSTOM_COLOR, zone.options.Color) if type(mySensor) == "table" then local percent = getCellPercent(getCellAvg(mySensor)) - lcd.drawText(zone.zone.x + zone.zone.w, zone.zone.y+5, percent.."% ", RIGHT + MIDSIZE + CUSTOM_COLOR) + lcd.drawText(zone.zone.x + zone.zone.w, zone.zone.y+5, percent.."% ", RIGHT + MIDSIZE + CUSTOM_COLOR + shadowed) -- fils batt lcd.setColor(CUSTOM_COLOR, getPercentColor(percent)) @@ -219,7 +221,7 @@ lcd.setColor(CUSTOM_COLOR, getRangeColor(mySensor[i], getCellMax(mySensor), getCellMax(mySensor) - 0.2)) lcd.drawFilledRectangle(zone.zone.x + pos[i].x, zone.zone.y + pos[i].y, 58, 20, CUSTOM_COLOR) lcd.setColor(CUSTOM_COLOR, WHITE) - lcd.drawText(zone.zone.x + pos[i].x+10, zone.zone.y + pos[i].y, string.format("%.2f", mySensor[i]), CUSTOM_COLOR) + lcd.drawText(zone.zone.x + pos[i].x+10, zone.zone.y + pos[i].y, string.format("%.2f", mySensor[i]), CUSTOM_COLOR + shadowed) lcd.drawRectangle(zone.zone.x + pos[i].x, zone.zone.y + pos[i].y, 59, 20, CUSTOM_COLOR,1) end else @@ -229,7 +231,7 @@ lcd.setColor(CUSTOM_COLOR, WHITE) lcd.drawRectangle(zone.zone.x + myBatt.x , zone.zone.y + myBatt.y, myBatt.w, myBatt.h, CUSTOM_COLOR, 2) lcd.drawFilledRectangle(zone.zone.x + myBatt.x + myBatt.w, zone.zone.y + myBatt.h/2 - myBatt.cath_h/2, myBatt.cath_w, myBatt.cath_h, CUSTOM_COLOR) - lcd.drawText(zone.zone.x + myBatt.x + 5 , zone.zone.y + myBatt.y + 5, string.format("%2.1fV", getCellSum(mySensor)), LEFT + MIDSIZE + CUSTOM_COLOR) + lcd.drawText(zone.zone.x + myBatt.x + 5 , zone.zone.y + myBatt.y + 5, string.format("%2.1fV", getCellSum(mySensor)), LEFT + MIDSIZE + CUSTOM_COLOR + shadowed) --for i=1, myBatt.w - myBatt.segments_w, myBatt.segments_w do -- lcd.drawRectangle(zone.zone.x + myBatt.x + i, zone.zone.y + myBatt.y, myBatt.segments_w, myBatt.h, CUSTOM_COLOR, 1) --end @@ -244,9 +246,9 @@ lcd.setColor(CUSTOM_COLOR, zone.options.Color) if type(mySensor) == "table" then local percent = getCellPercent(getCellAvg(mySensor)) - lcd.drawText(zone.zone.x+zone.zone.w, zone.zone.y+15, percent.."%", RIGHT + DBLSIZE + CUSTOM_COLOR) - lcd.drawText(zone.zone.x+zone.zone.w, zone.zone.y+44, string.format("%2.1fV", getCellSum(mySensor)), RIGHT + MIDSIZE + CUSTOM_COLOR) - lcd.drawText(zone.zone.x+zone.zone.w, zone.zone.y+65, getCellCount(mySensor).."S", RIGHT + MIDSIZE + CUSTOM_COLOR) + lcd.drawText(zone.zone.x+zone.zone.w, zone.zone.y+15, percent.."%", RIGHT + DBLSIZE + CUSTOM_COLOR + shadowed) + lcd.drawText(zone.zone.x+zone.zone.w, zone.zone.y+44, string.format("%2.1fV", getCellSum(mySensor)), RIGHT + MIDSIZE + CUSTOM_COLOR + shadowed) + lcd.drawText(zone.zone.x+zone.zone.w, zone.zone.y+65, getCellCount(mySensor).."S", RIGHT + MIDSIZE + CUSTOM_COLOR + shadowed) -- fils batt lcd.setColor(CUSTOM_COLOR, getPercentColor(percent)) lcd.drawFilledRectangle(zone.zone.x + myBatt.x, zone.zone.y + myBatt.y + myBatt.h + myBatt.cath_h - math.floor(percent/100 * myBatt.h), myBatt.w, math.floor(percent/100 * myBatt.h), CUSTOM_COLOR) @@ -256,11 +258,11 @@ lcd.setColor(CUSTOM_COLOR, getRangeColor(mySensor[i], getCellMax(mySensor), getCellMax(mySensor) - 0.2)) lcd.drawFilledRectangle(zone.zone.x + pos[i].x, zone.zone.y + pos[i].y, 58, 20, CUSTOM_COLOR) lcd.setColor(CUSTOM_COLOR, WHITE) - lcd.drawText(zone.zone.x + pos[i].x+10, zone.zone.y + pos[i].y, string.format("%.2f", mySensor[i]), CUSTOM_COLOR) + lcd.drawText(zone.zone.x + pos[i].x+10, zone.zone.y + pos[i].y, string.format("%.2f", mySensor[i]), CUSTOM_COLOR + shadowed) lcd.drawRectangle(zone.zone.x + pos[i].x, zone.zone.y + pos[i].y, 59, 20, CUSTOM_COLOR, 1) end else - lcd.drawText(zone.zone.x+5, zone.zone.y, "No FLVSS sensor data", LEFT + SMLSIZE + INVERS + CUSTOM_COLOR) + lcd.drawText(zone.zone.x+5, zone.zone.y, "No FLVSS sensor data", LEFT + SMLSIZE + INVERS + CUSTOM_COLOR + shadowed) end -- draws bat lcd.setColor(CUSTOM_COLOR, WHITE) @@ -285,16 +287,16 @@ lcd.drawFilledRectangle(zone.zone.x + myBatt.x, zone.zone.y + myBatt.y + myBatt.h + myBatt.cath_h - math.floor(percent/100 * myBatt.h), myBatt.w, math.floor(percent/100 * myBatt.h), CUSTOM_COLOR) -- draw right text section lcd.setColor(CUSTOM_COLOR, zone.options.Color) - lcd.drawText(zone.zone.x+zone.zone.w, zone.zone.y + myBatt.y, percent.."%", RIGHT + DBLSIZE + CUSTOM_COLOR) - lcd.drawText(zone.zone.x+zone.zone.w, zone.zone.y + myBatt.y + 63, string.format("%2.1fV", getCellSum(mySensor)), RIGHT + MIDSIZE + CUSTOM_COLOR) - lcd.drawText(zone.zone.x+zone.zone.w, zone.zone.y + myBatt.y + 105, getCellCount(mySensor).."S", RIGHT + MIDSIZE + CUSTOM_COLOR) + lcd.drawText(zone.zone.x+zone.zone.w, zone.zone.y + myBatt.y, percent.."%", RIGHT + DBLSIZE + CUSTOM_COLOR + shadowed) + lcd.drawText(zone.zone.x+zone.zone.w, zone.zone.y + myBatt.y + 63, string.format("%2.1fV", getCellSum(mySensor)), RIGHT + MIDSIZE + CUSTOM_COLOR + shadowed) + lcd.drawText(zone.zone.x+zone.zone.w, zone.zone.y + myBatt.y + 105, getCellCount(mySensor).."S", RIGHT + MIDSIZE + CUSTOM_COLOR + shadowed) -- draw cells local pos = {{x=111, y=38}, {x=164, y=38}, {x=217, y=38}, {x=111, y=57}, {x=164, y=57}, {x=217, y=57}} for i=1, getCellCount(mySensor), 1 do lcd.setColor(CUSTOM_COLOR, getRangeColor(mySensor[i], getCellMax(mySensor), getCellMax(mySensor) - 0.2)) lcd.drawFilledRectangle(zone.zone.x + pos[i].x, zone.zone.y + pos[i].y, 53, 20, CUSTOM_COLOR) lcd.setColor(CUSTOM_COLOR, WHITE) - lcd.drawText(zone.zone.x + pos[i].x+10, zone.zone.y + pos[i].y, string.format("%.2f", mySensor[i]), CUSTOM_COLOR) + lcd.drawText(zone.zone.x + pos[i].x+10, zone.zone.y + pos[i].y, string.format("%.2f", mySensor[i]), CUSTOM_COLOR + shadowed) lcd.drawRectangle(zone.zone.x + pos[i].x, zone.zone.y + pos[i].y, 54, 20, CUSTOM_COLOR, 1) end -- draw cells for lowest cells @@ -304,7 +306,7 @@ lcd.drawFilledRectangle(zone.zone.x + pos[i].x, zone.zone.y + pos[i].y, 53, 20, CUSTOM_COLOR) lcd.setColor(CUSTOM_COLOR, WHITE) lcd.drawRectangle(zone.zone.x + pos[i].x, zone.zone.y + pos[i].y, 54, 20, CUSTOM_COLOR, 1) - lcd.drawText(zone.zone.x + pos[i].x+10, zone.zone.y + pos[i].y, string.format("%.2f", histCellData[i]), CUSTOM_COLOR) + lcd.drawText(zone.zone.x + pos[i].x+10, zone.zone.y + pos[i].y, string.format("%.2f", histCellData[i]), CUSTOM_COLOR + shadowed) end else lcd.drawText(zone.zone.x+5, zone.zone.y, "No FLVSS sensor data", LEFT + SMLSIZE + INVERS + CUSTOM_COLOR) @@ -318,9 +320,9 @@ end -- draw middle rectangles lcd.drawRectangle(zone.zone.x + 110, zone.zone.y + 38, 161, 40, CUSTOM_COLOR, 1) - lcd.drawText(zone.zone.x + 270, zone.zone.y + 21, "Live data", RIGHT + SMLSIZE + INVERS + CUSTOM_COLOR) + lcd.drawText(zone.zone.x + 270, zone.zone.y + 21, "Live data", RIGHT + SMLSIZE + INVERS + CUSTOM_COLOR + shadowed) lcd.drawRectangle(zone.zone.x + 110, zone.zone.y + 110, 161, 40, CUSTOM_COLOR, 1) - lcd.drawText(zone.zone.x + 270, zone.zone.y + 93, "Lowest data", RIGHT + SMLSIZE + INVERS + CUSTOM_COLOR) + lcd.drawText(zone.zone.x + 270, zone.zone.y + 93, "Lowest data", RIGHT + SMLSIZE + INVERS + CUSTOM_COLOR + shadowed) return end @@ -331,6 +333,11 @@ end function refresh(myZone) + if myZone.options.Shadow == 1 then + shadowed = SHADOWED + else + shadowed = 0 + end if myZone.options.Sensor == 1 then lcd.drawText(myZone.zone.x+2, myZone.zone.y+2, "Not configured", LEFT + SMLSIZE + CUSTOM_COLOR) lcd.drawText(myZone.zone.x+2, myZone.zone.y+20, "Requires FLVSS sensor", LEFT + SMLSIZE + INVERS + CUSTOM_COLOR) diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/WIDGETS/Counter/main.lua opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/WIDGETS/Counter/main.lua --- opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/horus/WIDGETS/Counter/main.lua 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/horus/WIDGETS/Counter/main.lua 2017-10-31 16:16:43.000000000 +0000 @@ -1,7 +1,24 @@ +---- ######################################################################### +---- # # +---- # Copyright (C) OpenTX # +-----# # +---- # License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html # +---- # # +---- # This program is free software; you can redistribute it and/or modify # +---- # it under the terms of the GNU General Public License version 2 as # +---- # published by the Free Software Foundation. # +---- # # +---- # 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. # +---- # # +---- ######################################################################### local options = { { "Option1", SOURCE, 1 }, { "Option2", VALUE, 1000 }, - { "Option3", COLOR, RED } + { "Option3", COLOR, RED }, + { "Shadow", BOOL, 0 } } local function create(zone, options) @@ -20,7 +37,11 @@ function refresh(pie) pie.counter = pie.counter + 1 - lcd.drawNumber(pie.zone.x, pie.zone.y, pie.counter, LEFT + DBLSIZE + TEXT_COLOR); + if pie.options.Shadow == 1 then + lcd.drawNumber(pie.zone.x, pie.zone.y, pie.counter, LEFT + DBLSIZE + TEXT_COLOR); + else + lcd.drawNumber(pie.zone.x, pie.zone.y, pie.counter, LEFT + DBLSIZE + TEXT_COLOR + SHADOWED); + end end return { name="Counter", options=options, create=create, update=update, refresh=refresh, background=background } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x7/CROSSFIRE/crossfire.lua opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x7/CROSSFIRE/crossfire.lua --- opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x7/CROSSFIRE/crossfire.lua 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x7/CROSSFIRE/crossfire.lua 2017-10-31 16:16:43.000000000 +0000 @@ -0,0 +1,116 @@ +---- ######################################################################### +---- # # +---- # Copyright (C) OpenTX # +-----# # +---- # License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html # +---- # # +---- # This program is free software; you can redistribute it and/or modify # +---- # it under the terms of the GNU General Public License version 2 as # +---- # published by the Free Software Foundation. # +---- # # +---- # 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. # +---- # # +---- ######################################################################### +local devices = { } +local lineIndex = 1 +local pageOffset = 0 + +local function createDevice(id, name) + local device = { + id = id, + name = name, + timeout = 0 + } + return device +end + +local function getDevice(name) + for i=1, #devices do + if devices[i].name == name then + return devices[i] + end + end + return nil +end + +local function parseDeviceInfoMessage(data) + local id = data[2] + local name = "" + local i = 3 + while data[i] ~= 0 do + name = name .. string.char(data[i]) + i = i + 1 + end + local device = getDevice(name) + if device == nil then + device = createDevice(id, name) + devices[#devices + 1] = device + end + local time = getTime() + device.timeout = time + 3000 -- 30s + if lineIndex == 0 then + lineIndex = 1 + end +end + +local devicesRefreshTimeout = 0 +local function refreshNext() + local command, data = crossfireTelemetryPop() + if command == nil then + local time = getTime() + if time > devicesRefreshTimeout then + devicesRefreshTimeout = time + 100 -- 1s + crossfireTelemetryPush(0x28, { 0x00, 0xEA }) + end + elseif command == 0x29 then + parseDeviceInfoMessage(data) + end +end + +local function selectDevice(step) + lineIndex = 1 + ((lineIndex + step - 1 + #devices) % #devices) +end + +-- Init +local function init() + lineIndex = 0 + pageOffset = 0 +end + +-- Main +local function run(event) + if event == nil then + error("Cannot be run as a model script!") + return 2 + elseif event == EVT_EXIT_BREAK then + return 2 + elseif event == EVT_ROT_LEFT then + selectDevice(1) + elseif event == EVT_ROT_RIGHT then + selectDevice(-1) + end + + lcd.clear() + lcd.drawScreenTitle("CROSSFIRE SETUP", 0, 0) + if #devices == 0 then + lcd.drawText(24, 28, "Waiting for Crossfire devices...") + else + for i=1, #devices do + local attr = (lineIndex == i and INVERS or 0) + if event == EVT_ROT_BREAK and attr == INVERS then + crossfireTelemetryPush(0x28, { devices[i].id, 0xEA }) + return "device.lua" + end + lcd.drawText(0, i*8+9, devices[i].name, attr) + end + end + + refreshNext() + + return 0 +end + +return { init=init, run=run } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x7/CROSSFIRE/device.lua opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x7/CROSSFIRE/device.lua --- opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x7/CROSSFIRE/device.lua 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x7/CROSSFIRE/device.lua 2017-10-31 16:16:43.000000000 +0000 @@ -0,0 +1,526 @@ +---- ######################################################################### +---- # # +---- # Copyright (C) OpenTX # +-----# # +---- # License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html # +---- # # +---- # This program is free software; you can redistribute it and/or modify # +---- # it under the terms of the GNU General Public License version 2 as # +---- # published by the Free Software Foundation. # +---- # # +---- # 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. # +---- # # +---- ######################################################################### +local deviceId = 0 +local deviceName = "" +local lineIndex = 0 +local pageOffset = 0 +local edit = false +local charIndex = 1 +local fieldPopup +local fieldTimeout = 0 +local fieldId = 1 +local fieldChunk = 0 +local fieldData = {} +local fields = {} + +local function getField(line) + local counter = 1 + for i = 1, #fields do + local field = fields[i] + if not field.hidden then + if counter < line then + counter = counter + 1 + else + return field + end + end + end +end + +local function initLineIndex() + lineIndex = 0 + for i = 1, #fields do + local field = getField(i) + if field and field.type ~= 11 and field.type ~= 12 and field.name ~= nil then + lineIndex = i + break + end + end +end + +-- Change display attribute to current field +local function incrField(step) + local field = getField(lineIndex) + if field.type == 10 then + local byte = 32 + if charIndex <= #field.value then + byte = string.byte(field.value, charIndex) + step + end + if byte < 32 then + byte = 32 + elseif byte > 122 then + byte = 122 + end + if charIndex <= #field.value then + field.value = string.sub(field.value, 1, charIndex-1) .. string.char(byte) .. string.sub(field.value, charIndex+1) + else + field.value = field.value .. string.char(byte) + end + else + local min, max = 0, 0 + if field.type <= 5 then + min = field.min + max = field.max + step = field.step * step + elseif field.type == 9 then + min = 0 + max = #field.values - 1 + end + if (step < 0 and field.value > min) or (step > 0 and field.value < max) then + field.value = field.value + step + end + end +end + +-- Select the next or previous editable field +local function selectField(step) + local newLineIndex = lineIndex + local field + repeat + newLineIndex = newLineIndex + step + if newLineIndex == 0 then + newLineIndex = #fields + elseif newLineIndex == 1 + #fields then + newLineIndex = 1 + pageOffset = 0 + end + field = getField(newLineIndex) + until newLineIndex == lineIndex or (field and field.type ~= 11 and field.name) + lineIndex = newLineIndex + if lineIndex > 7 + pageOffset then + pageOffset = lineIndex - 7 + elseif lineIndex <= pageOffset then + pageOffset = lineIndex - 1 + end +end + +local function split(str) + local t = {} + local i = 1 + for s in string.gmatch(str, "([^;]+)") do + t[i] = s + i = i + 1 + end + return t +end + +local function fieldGetString(data, offset) + local result = "" + while data[offset] ~= 0 do + result = result .. string.char(data[offset]) + offset = offset + 1 + end + offset = offset + 1 + return result, offset +end + +local function parseDeviceInfoMessage(data) + local offset + deviceId = data[2] + deviceName, offset = fieldGetString(data, 3) + local fields_count = data[offset+12] + for i=1, fields_count do + fields[i] = { name=nil } + end +end + +local function fieldGetValue(data, offset, size) + local result = 0 + for i=0, size-1 do + result = bit32.lshift(result, 8) + data[offset + i] + end + return result +end + +local function fieldUnsignedLoad(field, data, offset, size) + field.value = fieldGetValue(data, offset, size) + field.min = fieldGetValue(data, offset+size, size) + field.max = fieldGetValue(data, offset+2*size, size) + field.default = fieldGetValue(data, offset+3*size, size) + field.unit, offset = fieldGetString(data, offset+4*size) + field.step = 1 +end + +local function fieldUnsignedToSigned(field, size) + local bandval = bit32.lshift(0x80, (size-1)*8) + field.value = field.value - bit32.band(field.value, bandval) * 2 + field.min = field.min - bit32.band(field.min, bandval) * 2 + field.max = field.max - bit32.band(field.max, bandval) * 2 + field.default = field.default - bit32.band(field.default, bandval) * 2 +end + + local function fieldSignedLoad(field, data, offset, size) + fieldUnsignedLoad(field, data, offset, size) + fieldUnsignedToSigned(field, size) +end + +local function fieldIntSave(index, value, size) + local frame = { deviceId, 0xEA, index } + for i=size-1, 0, -1 do + frame[#frame + 1] = (bit32.rshift(value, 8*i) % 256) + end + crossfireTelemetryPush(0x2D, frame) +end + +local function fieldUnsignedSave(field, size) + local value = field.value + fieldIntSave(field.id, value, size) +end + +local function fieldSignedSave(field, size) + local value = field.value + if value < 0 then + value = bit32.lshift(0x100, (size-1)*8) + value + end + fieldIntSave(field.id, value, size) +end + +local function fieldIntDisplay(field, y, attr) + lcd.drawNumber(89, y, field.value, LEFT + attr) + lcd.drawText(lcd.getLastPos(), y, field.unit, attr) +end + +-- UINT8 +local function fieldUint8Load(field, data, offset) + fieldUnsignedLoad(field, data, offset, 1) +end + +local function fieldUint8Save(field) + fieldUnsignedSave(field, 1) +end + +-- INT8 +local function fieldInt8Load(field, data, offset) + fieldSignedLoad(field, data, offset, 1) +end + +local function fieldInt8Save(field) + fieldSignedSave(field, 1) +end + +-- UINT16 +local function fieldUint16Load(field, data, offset) + fieldUnsignedLoad(field, data, offset, 2) +end + +local function fieldUint16Save(field) + fieldUnsignedSave(field, 2) +end + +-- INT16 +local function fieldInt16Load(field, data, offset) + fieldSignedLoad(field, data, offset, 2) +end + +local function fieldInt16Save(field) + fieldSignedSave(field, 2) +end + +-- FLOAT +local function fieldFloatLoad(field, data, offset) + field.value = fieldGetValue(data, offset, 4) + field.min = fieldGetValue(data, offset+4, 4) + field.max = fieldGetValue(data, offset+8, 4) + field.default = fieldGetValue(data, offset+12, 4) + fieldUnsignedToSigned(field, 4) + field.prec = data[offset+16] + if field.prec > 2 then + field.prec = 2 + end + field.step = fieldGetValue(data, offset+17, 4) + field.unit, offset = fieldGetString(data, offset+21) +end + +local function fieldFloatDisplay(field, y, attr) + local attrnum + if field.prec == 1 then + attrnum = LEFT + attr + PREC1 + elseif field.prec == 2 then + attrnum = LEFT + attr + PREC2 + else + attrnum = LEFT + attr + end + lcd.drawNumber(89, y, field.value, attrnum) + lcd.drawText(lcd.getLastPos(), y, field.unit, attr) +end + +local function fieldFloatSave(field) + fieldUnsignedSave(field, 4) +end + +-- TEXT SELECTION +local function fieldTextSelectionLoad(field, data, offset) + local values + values, offset = fieldGetString(data, offset) + if values ~= "" then + field.values = split(values) + end + field.value = data[offset] + field.min = data[offset+1] + field.max = data[offset+2] + field.default = data[offset+3] + field.unit, offset = fieldGetString(data, offset+4) +end + +local function fieldTextSelectionSave(field) + crossfireTelemetryPush(0x2D, { deviceId, 0xEA, field.id, field.value }) +end + +local function fieldTextSelectionDisplay(field, y, attr) + lcd.drawText(89, y, field.values[field.value+1], attr) + lcd.drawText(lcd.getLastPos(), y, field.unit, attr) +end + +-- STRING +local function fieldStringLoad(field, data, offset) + field.value, offset = fieldGetString(data, offset) + if #data >= offset then + field.maxlen = data[offset] + end +end + +local function fieldStringSave(field) + local frame = { deviceId, 0xEA, field.id } + for i=1, string.len(field.value) do + frame[#frame + 1] = string.byte(field.value, i) + end + frame[#frame + 1] = 0 + crossfireTelemetryPush(0x2D, frame) +end + +local function fieldStringDisplay(field, y, attr) + if edit == true and attr then + lcd.drawText(89, y, field.value, FIXEDWIDTH) + lcd.drawText(83+6*charIndex, y, string.sub(field.value, charIndex, charIndex), FIXEDWIDTH + attr) + else + lcd.drawText(89, y, field.value, attr) + end +end + +local function fieldCommandLoad(field, data, offset) + field.status = data[offset] + field.timeout = data[offset+1] + field.info, offset = fieldGetString(data, offset+2) + if field.status < 2 or field.status > 3 then + fieldPopup = nil + end +end + +local function fieldCommandSave(field) + if field.status == 0 then + field.status = 1 + crossfireTelemetryPush(0x2D, { deviceId, 0xEA, field.id, field.status }) + fieldPopup = field + fieldTimeout = getTime() + field.timeout + end +end + +local function fieldCommandDisplay(field, y, attr) + lcd.drawText(0, y, field.name, attr) + if field.info ~= "" then + lcd.drawText(89, y, "[" .. field.info .. "]") + end +end + +local functions = { + { load=fieldUint8Load, save=fieldUint8Save, display=fieldIntDisplay }, + { load=fieldInt8Load, save=fieldInt8Save, display=fieldIntDisplay }, + { load=fieldUint16Load, save=fieldUint16Save, display=fieldIntDisplay }, + { load=fieldInt16Load, save=fieldInt16Save, display=fieldIntDisplay }, + nil, + nil, + nil, + nil, + { load=fieldFloatLoad, save=fieldFloatSave, display=fieldFloatDisplay }, + { load=fieldTextSelectionLoad, save=fieldTextSelectionSave, display=fieldTextSelectionDisplay }, + { load=fieldStringLoad, save=fieldStringSave, display=fieldStringDisplay }, + nil, + { load=fieldStringLoad, save=fieldStringSave, display=fieldStringDisplay }, + { load=fieldCommandLoad, save=fieldCommandSave, display=fieldCommandDisplay }, +} + +local function parseParameterInfoMessage(data) + if data[2] ~= deviceId or data[3] ~= fieldId then + fieldData = {} + fieldChunk = 0 + return + end + local field = fields[fieldId] + local chunks = data[4] + for i=5, #data do + fieldData[#fieldData + 1] = data[i] + end + if chunks > 0 then + fieldChunk = fieldChunk + 1 + else + fieldChunk = 0 + field.id = fieldId + field.parent = fieldData[1] + field.type = fieldData[2] % 128 + field.hidden = (bit32.rshift(fieldData[2], 7) == 1) + local name, i = fieldGetString(fieldData, 3) + if name ~= "" then + local indent = "" + local parent = field.parent + while parent ~= 0 do + indent = indent .. " " + parent = fields[parent].parent + end + field.name = indent .. name + end + if functions[field.type+1] then + functions[field.type+1].load(field, fieldData, i) + end + if not fieldPopup then + if lineIndex == 0 and field.hidden ~= true and field.type and field.type ~= 11 and field.type ~= 12 then + initLineIndex() + end + fieldId = 1 + (fieldId % #fields) + end + fieldData = {} + end +end + +local function refreshNext() + local command, data = crossfireTelemetryPop() + if command == nil then + local time = getTime() + if fieldPopup then + if time > fieldTimeout then + local frame = { deviceId, 0xEA, fieldPopup.id } + crossfireTelemetryPush(0x2D, frame) + fieldTimeout = time + fieldPopup.timeout + end + elseif time > fieldTimeout and not edit then + crossfireTelemetryPush(0x2C, { deviceId, 0xEA, fieldId, fieldChunk }) + fieldTimeout = time + 200 -- 2s + end + elseif command == 0x29 then + parseDeviceInfoMessage(data) + elseif command == 0x2B then + parseParameterInfoMessage(data) + fieldTimeout = 0 + end +end + +-- Main +local function runDevicePage(event) + if event == EVT_EXIT_BREAK then -- exit script + if edit == true then + edit = false + local field = getField(lineIndex) + fieldTimeout = getTime() + 200 -- 2s + fieldId, fieldChunk = field.id, 0 + fieldData = {} + functions[field.type+1].save(field) + else + return "crossfire.lua" + end + elseif event == EVT_ROT_BREAK then -- toggle editing/selecting current field + local field = getField(lineIndex) + if field.name then + if field.type == 10 then + if edit == false then + edit = true + charIndex = 1 + else + charIndex = charIndex + 1 + end + elseif field.type < 11 then + edit = not edit + end + if edit == false then + fieldTimeout = getTime() + 200 -- 2s + fieldId, fieldChunk = field.id, 0 + fieldData = {} + functions[field.type+1].save(field) + end + end + elseif edit then + if event == EVT_ROT_RIGHT then + incrField(1) + elseif event == EVT_ROT_LEFT then + incrField(-1) + end + else + if event == EVT_ROT_RIGHT then + selectField(1) + elseif event == EVT_ROT_LEFT then + selectField(-1) + end + end + + lcd.clear() + lcd.drawScreenTitle(deviceName, 0, 0) + for y = 1, 7 do + local field = getField(pageOffset+y) + if not field then + break + elseif field.name == nil then + lcd.drawText(0, 1+8*y, "...") + else + local attr = lineIndex == (pageOffset+y) and ((edit == true and BLINK or 0) + INVERS) or 0 + lcd.drawText(0, 1+8*y, field.name) + if functions[field.type+1] then + functions[field.type+1].display(field, 1+8*y, attr) + end + end + end + + return 0 +end + +local function runPopupPage(event) + local result + if fieldPopup.status == 3 then + result = popupConfirmation(fieldPopup.info, event) + else + result = popupWarning(fieldPopup.info, event) + end + if result == "OK" then + crossfireTelemetryPush(0x2D, { deviceId, 0xEA, fieldPopup.id, 4 }) + elseif result == "CANCEL" then + crossfireTelemetryPush(0x2D, { deviceId, 0xEA, fieldPopup.id, 5 }) + end + return 0 +end + +-- Init +local function init() + lineIndex, edit = 0, false +end + +-- Main +local function run(event) + if event == nil then + error("Cannot be run as a model script!") + return 2 + end + + local result + if fieldPopup ~= nil then + result = runPopupPage(event) + else + result = runDevicePage(event) + end + + refreshNext() + + return result +end + +return { init=init, run=run } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x7/S6R/S6R_Calibrate.lua opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x7/S6R/S6R_Calibrate.lua --- opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x7/S6R/S6R_Calibrate.lua 2017-05-14 17:18:57.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x7/S6R/S6R_Calibrate.lua 1970-01-01 00:00:00.000000000 +0000 @@ -1,283 +0,0 @@ -local VALUE = 0 -local COMBO = 1 - -local COLUMN_2 = 150 - -local edit = false -local page = 1 -local current = 1 -local refreshState = 0 -local refreshIndex = 0 -local calibrationState = 0 -local pageOffset = 0 -local calibrationStep = 0 -local pages = {} -local fields = {} -local modifications = {} -local positionConfirmed = 0 -local orientationAutoSense = 0 - -local calibrationFields = { - {"X:", VALUE, 0x9E, 0, -100, 100, "%"}, - {"Y:", VALUE, 0x9F, 0, -100, 100, "%"}, - {"Z:", VALUE, 0xA0, 0, -100, 100, "%"} -} - -local function drawProgressBar() - local width = (140 * refreshIndex) / #fields - lcd.drawRectangle(30, 1, 144, 6) - lcd.drawFilledRectangle(32, 3, width, 2); -end - --- Select the next or previous page -local function selectPage(step) - page = 1 + ((page + step - 1 + #pages) % #pages) - refreshIndex = 0 - calibrationStep = 0 - pageOffset = 0 -end - --- Draw initial warning page -local function runWarningPage(event) - lcd.clear() - lcd.drawScreenTitle("S6R Calibration", page, #pages) - lcd.drawText(0, 10, "You only need to calibrate", SMLSIZE) - lcd.drawText(0, 20, "once. You will need the S6R,", SMLSIZE) - lcd.drawText(0, 30, "power, and a level surface.", SMLSIZE) - lcd.drawText(0, 40, "Press [Enter] when ready", SMLSIZE) - lcd.drawText(0, 50, "Press [Exit] to cancel", SMLSIZE) - if event == EVT_ENTER_BREAK then - selectPage(1) - return 0 - elseif event == EVT_EXIT_BREAK then - return 2 - end - return 0 -end - --- Redraw the current page -local function redrawFieldsPage() - lcd.clear() - lcd.drawScreenTitle("S6R Calibration", page, #pages) - - if refreshIndex < #fields then - drawProgressBar() - end - - for index = 1, 7, 1 do - local field = fields[pageOffset+index] - if field == nil then - break - end - - local attr = current == (pageOffset+index) and ((edit == true and BLINK or 0) + INVERS) or 0 - - lcd.drawText(0, 1+8*index, field[1]) - - if field[4] == nil then - lcd.drawText(COLUMN_2, 1+8*index, "---", attr) - else - if field[2] == VALUE then - lcd.drawNumber(COLUMN_2, 1+8*index, field[4], LEFT + attr) - elseif field[2] == COMBO then - if field[4] >= 0 and field[4] < #(field[5]) then - lcd.drawText(COLUMN_2, 1+8*index, field[5][1+field[4]], attr) - end - end - end - end -end - -local function telemetryRead(field) - return sportTelemetryPush(0x17, 0x30, 0x0C30, field) -end - -local function telemetryWrite(field, value) - return sportTelemetryPush(0x17, 0x31, 0x0C30, field + value*256) -end - -local telemetryPopTimeout = 0 -local function refreshNext() - if refreshState == 0 then - if calibrationState == 1 then - if telemetryWrite(0x9D, calibrationStep) == true then - refreshState = 1 - calibrationState = 2 - telemetryPopTimeout = getTime() + 80 -- normal delay is 500ms - end - elseif #modifications > 0 then - telemetryWrite(modifications[1][1], modifications[1][2]) - modifications[1] = nil - elseif refreshIndex < #fields then - local field = fields[refreshIndex + 1] - if telemetryRead(field[3]) == true then - refreshState = 1 - telemetryPopTimeout = getTime() + 80 -- normal delay is 500ms - end - end - elseif refreshState == 1 then - local physicalId, primId, dataId, value = sportTelemetryPop() - if physicalId == 0x1A and primId == 0x32 and dataId == 0x0C30 then - local fieldId = value % 256 - if calibrationState == 2 then - if fieldId == 0x9D then - refreshState = 0 - calibrationState = 0 - calibrationStep = (calibrationStep + 1) % 7 - end - else - local field = fields[refreshIndex + 1] - if fieldId == field[3] then - local value = math.floor(value / 256) - if field[3] >= 0x9E and field[3] <= 0xA0 then - local b1 = value % 256 - local b2 = math.floor(value / 256) - value = b1*256 + b2 - value = value - bit32.band(value, 0x8000) * 2 - end - if field[2] == COMBO and #field == 6 then - for index = 1, #(field[6]), 1 do - if value == field[6][index] then - value = index - 1 - break - end - end - elseif field[2] == VALUE and #field == 8 then - value = value - field[8] + field[5] - end - fields[refreshIndex + 1][4] = value - refreshIndex = refreshIndex + 1 - refreshState = 0 - end - end - elseif getTime() > telemetryPopTimeout then - refreshState = 0 - calibrationState = 0 - end - end -end - -local function updateField(field) - local value = field[4] - if field[2] == COMBO and #field == 6 then - value = field[6][1+value] - elseif field[2] == VALUE and #field == 8 then - value = value + field[8] - field[5] - end - modifications[#modifications+1] = { field[3], value } -end - --- Main -local function runFieldsPage(event) - if event == EVT_EXIT_BREAK then -- exit script - return 2 - elseif event == EVT_ENTER_BREAK then -- toggle editing/selecting current field - if fields[current][4] ~= nil then - edit = not edit - if edit == false then - updateField(fields[current]) - end - end - elseif edit then - if event == EVT_PLUS_FIRST or event == EVT_ROT_RIGHT or event == EVT_PLUS_REPT then - addField(1) - elseif event == EVT_MINUS_FIRST or event == EVT_ROT_LEFT or event == EVT_MINUS_REPT then - addField(-1) - end - else - if event == EVT_MINUS_FIRST or event == EVT_ROT_LEFT then - selectField(1) - elseif event == EVT_PLUS_FIRST or event == EVT_ROT_RIGHT then - selectField(-1) - end - end - redrawFieldsPage() - return 0 -end - -local function drawCalibrationOrientation(x, y, step) - local orientation = { {"Label up.", "", 0, 0, 1000, 0, 0, 1000}, - {"Label down.", "", 0, 0, -1000, 0, 0, -1000}, - {"Pins Up.", "", -1000, 0, 0, 1000, 0, 0}, - {"Pins Down.", "", 1000, 0, 0, -1000, 0, 0}, - {"Label facing you", "Pins Right", 0, 1000, 0, 0, -1000, 0}, - {"Label facing you", "Pins Left", 0, -1000 , 0, 0, 1000, 0} } - - lcd.drawText(0, 9, "Place the S6R as follows:", 0) - lcd.drawText(x-9, y, orientation[step][1]) - lcd.drawText(x-9, y+10, orientation[step][2]) - local positionStatus = 0 - for index = 1, 3, 1 do - local field = fields[index] - lcd.drawText(90, 12+10*index, field[1], 0) - if math.abs(field[4] - orientation[step][2+index+orientationAutoSense]) < 200 then - lcd.drawNumber(100, 12+10*index, field[4]/10, LEFT+PREC2) - positionStatus = positionStatus + 1 - else - lcd.drawNumber(100, 12+10*index, field[4]/10, LEFT+PREC2+INVERS) - end - end - if step == 3 and positionStatus == 2 then -- orientation auto sensing - orientationAutoSense = 3 - orientationAutoSense - end - if positionStatus == 3 then - lcd.drawText(0, 56, " [Enter] to validate ", INVERS) - positionConfirmed = 1 - end -end - -local function runCalibrationPage(event) - fields = calibrationFields - if refreshIndex == #fields then - refreshIndex = 0 - end - lcd.clear() - lcd.drawScreenTitle("S6R Calibration", page, #pages) - if(calibrationStep < 6) then - drawCalibrationOrientation(10, 24, 1 + calibrationStep) - - local attr = calibrationState == 0 and INVERS or 0 - --lcd.drawText(0, 56, "[Enter] to validate", attr) - else - lcd.drawText(0, 19, "Calibration completed", 0) --- lcd.drawText(10, 19, "Done",0) - lcd.drawText(0, 56, "Press [Exit] when ready", attr) - end - if calibrationStep > 6 and (event == EVT_ENTER_BREAK or event == EVT_EXIT_BREAK) then - return 2 - elseif event == EVT_ENTER_BREAK and positionConfirmed then - calibrationState = 1 - positionConfirmed = 0 - end - return 0 -end - - --- Init -local function init() - current, edit, refreshState, refreshIndex = 1, false, 0, 0 - pages = { - runWarningPage, - runCalibrationPage - } -end - --- Main -local function run(event) - if event == nil then - error("Cannot be run as a model script!") - return 2 - elseif event == EVT_PAGE_BREAK then - selectPage(1) - elseif event == EVT_PAGE_LONG then - killEvents(event); - selectPage(-1) - end - - local result = pages[page](event) - refreshNext() - - return result -end - -return { init=init, run=run } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x7/S6R/S6R.lua opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x7/S6R/S6R.lua --- opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x7/S6R/S6R.lua 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x7/S6R/S6R.lua 1970-01-01 00:00:00.000000000 +0000 @@ -1,256 +0,0 @@ -local VALUE = 0 -local COMBO = 1 - -local edit = false -local page = 1 -local current = 1 -local refreshState = 0 -local refreshIndex = 0 -local pageOffset = 0 -local pages = {} -local fields = {} -local modifications = {} - -local configFields = { - {"Wing type", COMBO, 0x80, nil, { "Normal", "Delta", "VTail" } }, - {"Mounting type", COMBO, 0x81, nil, { "Horz", "Horz rev.", "Vert", "Vert rev." } }, -} - -local settingsFields = { - {"S6R functions", COMBO, 0x9C, nil, { "Disable", "Enable" } }, - {"CH5 mode", COMBO, 0xA8, nil, { "AIL2", "AUX1" } }, - {"CH6 mode", COMBO, 0xA9, nil, { "ELE2", "AUX2" } }, - {"AIL direction", COMBO, 0x82, nil, { "Normal", "Invers" }, { 255, 0 } }, - {"ELE direction", COMBO, 0x83, nil, { "Normal", "Invers" }, { 255, 0 } }, - {"RUD direction", COMBO, 0x84, nil, { "Normal", "Invers" }, { 255, 0 } }, - {"AIL2 direction", COMBO, 0x9A, nil, { "Normal", "Invers" }, { 255, 0 } }, - {"ELE2 direction", COMBO, 0x9B, nil, { "Normal", "Invers" }, { 255, 0 } }, - {"AIL stab gain", VALUE, 0x85, nil, 0, 200, "%"}, - {"ELE stab gain", VALUE, 0x86, nil, 0, 200, "%"}, - {"RUD stab gain", VALUE, 0x87, nil, 0, 200, "%"}, - {"AIL autolvl gain", VALUE, 0x88, nil, 0, 200, "%"}, - {"ELE autolvl gain", VALUE, 0x89, nil, 0, 200, "%"}, - {"ELE hover gain", VALUE, 0x8C, nil, 0, 200, "%"}, - {"RUD hover gain", VALUE, 0x8D, nil, 0, 200, "%"}, - {"AIL knife gain", VALUE, 0x8E, nil, 0, 200, "%"}, - {"RUD knife gain", VALUE, 0x90, nil, 0, 200, "%"}, - {"AIL autolvl offset", VALUE, 0x91, nil, -20, 20, "%", 0x6C}, - {"ELE autolvl offset", VALUE, 0x92, nil, -20, 20, "%", 0x6C}, - {"ELE hover offset", VALUE, 0x95, nil, -20, 20, "%", 0x6C}, - {"RUD hover offset", VALUE, 0x96, nil, -20, 20, "%", 0x6C}, - {"AIL knife offset", VALUE, 0x97, nil, -20, 20, "%", 0x6C}, - {"RUD knife offset", VALUE, 0x99, nil, -20, 20, "%", 0x6C}, -} - --- Change display attribute to current field -local function addField(step) - local field = fields[current] - local min, max - if field[2] == VALUE then - min = field[5] - max = field[6] - elseif field[2] == COMBO then - min = 0 - max = #(field[5]) - 1 - end - if (step < 0 and field[4] > min) or (step > 0 and field[4] < max) then - field[4] = field[4] + step - end -end - --- Select the next or previous page -local function selectPage(step) - page = 1 + ((page + step - 1 + #pages) % #pages) - refreshIndex = 0 - pageOffset = 0 -end - --- Select the next or previous editable field -local function selectField(step) - current = 1 + ((current + step - 1 + #fields) % #fields) - if current > 7 + pageOffset then - pageOffset = current - 7 - elseif current <= pageOffset then - pageOffset = current - 1 - end -end - -local function drawProgressBar() - local width = (70 * refreshIndex) / #fields - lcd.drawRectangle(30, 1, 70, 6) - lcd.drawFilledRectangle(32, 3, width, 2); -end - --- Redraw the current page -local function redrawFieldsPage() - lcd.clear() - lcd.drawScreenTitle("S6R", page, #pages) - - if refreshIndex < #fields then - drawProgressBar() - end - - for index = 1, 7, 1 do - local field = fields[pageOffset+index] - if field == nil then - break - end - - local attr = current == (pageOffset+index) and ((edit == true and BLINK or 0) + INVERS) or 0 - - lcd.drawText(0, 1+8*index, field[1]) - - if field[4] == nil then - lcd.drawText(LCD_W, 1+8*index, "---", attr + RIGHT) - else - if field[2] == VALUE then - lcd.drawNumber(LCD_W, 1+8*index, field[4], attr + RIGHT) - elseif field[2] == COMBO then - if field[4] >= 0 and field[4] < #(field[5]) then - lcd.drawText(LCD_W, 1+8*index, field[5][1+field[4]], attr + RIGHT) - end - end - end - end -end - -local function telemetryRead(field) - return sportTelemetryPush(0x17, 0x30, 0x0C30, field) -end - -local function telemetryWrite(field, value) - return sportTelemetryPush(0x17, 0x31, 0x0C30, field + value*256) -end - -local telemetryPopTimeout = 0 -local function refreshNext() - if refreshState == 0 then - if #modifications > 0 then - telemetryWrite(modifications[1][1], modifications[1][2]) - modifications[1] = nil - elseif refreshIndex < #fields then - local field = fields[refreshIndex + 1] - if telemetryRead(field[3]) == true then - refreshState = 1 - telemetryPopTimeout = getTime() + 80 -- normal delay is 500ms - end - end - elseif refreshState == 1 then - local physicalId, primId, dataId, value = sportTelemetryPop() - if physicalId == 0x1A and primId == 0x32 and dataId == 0x0C30 then - local fieldId = value % 256 - local field = fields[refreshIndex + 1] - if fieldId == field[3] then - local value = math.floor(value / 256) - if field[3] >= 0x9E and field[3] <= 0xA0 then - local b1 = value % 256 - local b2 = math.floor(value / 256) - value = b1*256 + b2 - value = value - bit32.band(value, 0x8000) * 2 - end - if field[2] == COMBO and #field == 6 then - for index = 1, #(field[6]), 1 do - if value == field[6][index] then - value = index - 1 - break - end - end - elseif field[2] == VALUE and #field == 8 then - value = value - field[8] + field[5] - end - fields[refreshIndex + 1][4] = value - refreshIndex = refreshIndex + 1 - refreshState = 0 - end - elseif getTime() > telemetryPopTimeout then - refreshState = 0 - end - end -end - -local function updateField(field) - local value = field[4] - if field[2] == COMBO and #field == 6 then - value = field[6][1+value] - elseif field[2] == VALUE and #field == 8 then - value = value + field[8] - field[5] - end - modifications[#modifications+1] = { field[3], value } -end - --- Main -local function runFieldsPage(event) - if event == EVT_EXIT_BREAK then -- exit script - return 2 - elseif event == EVT_ENTER_BREAK then -- toggle editing/selecting current field - if fields[current][4] ~= nil then - edit = not edit - if edit == false then - updateField(fields[current]) - end - end - elseif edit then - if event == EVT_PLUS_FIRST or event == EVT_ROT_RIGHT or event == EVT_PLUS_REPT then - addField(1) - elseif event == EVT_MINUS_FIRST or event == EVT_ROT_LEFT or event == EVT_MINUS_REPT then - addField(-1) - end - else - if event == EVT_MINUS_FIRST or event == EVT_ROT_RIGHT then - selectField(1) - elseif event == EVT_PLUS_FIRST or event == EVT_ROT_LEFT then - selectField(-1) - end - end - redrawFieldsPage() - return 0 -end - -local mountText = { "Label is facing the sky", "Label is facing ground", "Label is left when", "Label is right when" } - -local function runConfigPage(event) - fields = configFields - local result = runFieldsPage(event) - if fields[2][4] ~= nil then - lcd.drawText(1, 30, "Pins toward tail") - lcd.drawText(1, 40, mountText[1 + fields[2][4]]) - if fields[2][4] > 1 then - lcd.drawText(1, 50, "looking from the tail") - end - end - return result -end - -local function runSettingsPage(event) - fields = settingsFields - return runFieldsPage(event) -end - --- Init -local function init() - current, edit, refreshState, refreshIndex = 1, false, 0, 0 - pages = { - runConfigPage, - runSettingsPage, - } -end - --- Main -local function run(event) - if event == nil then - error("Cannot be run as a model script!") - return 2 - elseif event == EVT_PAGE_BREAK then - selectPage(1) - elseif event == EVT_PAGE_LONG then - killEvents(event); - selectPage(-1) - end - - local result = pages[page](event) - refreshNext() - - return result -end - -return { init=init, run=run } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x7/SCRIPTS/TEMPLATES/readme.txt opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x7/SCRIPTS/TEMPLATES/readme.txt --- opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x7/SCRIPTS/TEMPLATES/readme.txt 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x7/SCRIPTS/TEMPLATES/readme.txt 1970-01-01 00:00:00.000000000 +0000 @@ -1 +0,0 @@ -This directory is for template lua scripts. diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x7/SCRIPTS/WIZARD/delta.lua opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x7/SCRIPTS/WIZARD/delta.lua --- opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x7/SCRIPTS/WIZARD/delta.lua 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x7/SCRIPTS/WIZARD/delta.lua 2017-12-17 16:22:27.000000000 +0000 @@ -0,0 +1,382 @@ +---- ######################################################################### +---- # # +---- # Copyright (C) OpenTX # +-----# # +---- # License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html # +---- # # +---- # This program is free software; you can redistribute it and/or modify # +---- # it under the terms of the GNU General Public License version 2 as # +---- # published by the Free Software Foundation. # +---- # # +---- # 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. # +---- # # +---- ######################################################################### +-- Delta Wizard pages +local ENGINE_PAGE = 0 +local ELEVONS_PAGE = 1 +local RUDDER_PAGE = 2 +local CONFIRMATION_PAGE = 3 + +-- Navigation variables +local page = ENGINE_PAGE +local dirty = true +local edit = false +local field = 0 +local fieldsMax = 0 + +-- Model settings +local engineMode = 1 +local thrCH1 = 0 +local elevCH1 = 0 +local elevCH2 = 0 +local elevonsMode = 0 +local rudderMode = 0 +local rudCH1 = 0 +local servoPage = nil + +-- Common functions +local lastBlink = 0 +local function blinkChanged() + local time = getTime() % 128 + local blink = (time - time % 64) / 64 + if blink ~= lastBlink then + lastBlink = blink + return true + else + return false + end +end + +local function fieldIncDec(event, value, max, force) + if edit or force==true then + if event == EVT_ROT_RIGHT then + value = (value + max) + dirty = true + elseif event == EVT_ROT_LEFT then + value = (value + max + 2) + dirty = true + end + value = (value % (max+1)) + end + return value +end + +local function valueIncDec(event, value, min, max) + if edit then + if event == EVT_ROT_RIGHT or event == EVT_ROT_RIGHT then + if value < max then + value = (value + 1) + dirty = true + end + elseif event == EVT_ROT_LEFT or event == EVT_ROT_LEFT then + if value > min then + value = (value - 1) + dirty = true + end + end + end + return value +end + +local function navigate(event, fieldMax, prevPage, nextPage) + if event == EVT_ENTER_BREAK then + edit = not edit + dirty = true + elseif edit then + if event == EVT_EXIT_BREAK then + edit = false + dirty = true + elseif not dirty then + dirty = blinkChanged() + end + else + if event == EVT_PAGE_BREAK then + page = nextPage + field = 0 + dirty = true + elseif event == EVT_PAGE_LONG then + page = prevPage + field = 0 + killEvents(event); + dirty = true + else + field = fieldIncDec(event, field, fieldMax, true) + end + end +end + +local function getFieldFlags(position) + flags = 0 + if field == position then + flags = INVERS + if edit then + flags = INVERS + BLINK + end + end + return flags +end + +local function channelIncDec(event, value) + if not edit and event==EVT_MENU_BREAK then + servoPage = value + dirty = true + else + value = valueIncDec(event, value, 0, 15) + end + return value +end + +-- Init function +local function init() + rudCH1 = defaultChannel(0) + thrCH1 = defaultChannel(2) + elevCH1 = defaultChannel(1) + elevCH2 = defaultChannel(3) +end + +-- Engine Menu +local engineModeItems = {"No", "Yes"} +local function drawEngineMenu() + lcd.clear() + if engineMode == 0 then + -- No engine + fieldsMax = 0 + else + -- 1 channel + lcd.drawText(5, 30, "Assign channel", 0); + lcd.drawText(5, 40, ">>>", 0); + lcd.drawSource(25, 40, MIXSRC_CH1+thrCH1, getFieldFlags(1)) + fieldsMax = 1 + end + lcd.drawText(1, 0, "Got an engine?", 0) + lcd.drawFilledRectangle(0, 0, LCD_W, 8, FILL_WHITE) + lcd.drawCombobox(0, 8, LCD_W, engineModeItems, engineMode, getFieldFlags(0)) +end + +local function engineMenu(event) + if dirty then + dirty = false + drawEngineMenu() + end + + navigate(event, fieldsMax, page, page+1) + + if field==0 then + engineMode = fieldIncDec(event, engineMode, 1) + elseif field==1 then + thrCH1 = channelIncDec(event, thrCH1) + end +end + +-- Elevons Menu +local elevonsModeItems = {"2 Channels"} +local function drawElevonsMenu() + lcd.clear() + lcd.drawText(1, 0, "Select elevon channnels", 0) + lcd.drawFilledRectangle(0, 0, LCD_W, 8, FILL_WHITE) + lcd.drawCombobox(0, 8, LCD_W, elevonsModeItems, elevonsMode, 0) + lcd.drawText(5, 30, "Assign channels", 0); + lcd.drawText(30, 40, "L", 0); + lcd.drawText(65, 40, "R", 0); + lcd.drawText(5, 50, ">>>", 0); + lcd.drawSource(25, 50, MIXSRC_CH1+elevCH1, getFieldFlags(0)) + lcd.drawSource(60, 50, MIXSRC_CH1+elevCH2, getFieldFlags(1)) + fieldsMax = 1 +end + +local function elevonsMenu(event) + if dirty then + dirty = false + drawElevonsMenu() + end + + navigate(event, fieldsMax, page-1, page+1) + + if field==0 then + elevCH1 = channelIncDec(event, elevCH1) + elseif field==1 then + elevCH2 = channelIncDec(event, elevCH2) + end +end + +-- Rudder menu +local rudderModeItems = {"No", "Yes"} + +local function drawRudderMenu() + lcd.clear() + if rudderMode == 0 then + -- No rudder + fieldsMax = 0 + else + -- 1 channel + lcd.drawText(5, 30, "Assign channel", 0); + lcd.drawText(5, 40, ">>>", 0); + lcd.drawSource(25, 40, MIXSRC_CH1+rudCH1, getFieldFlags(1)) + fieldsMax = 1 + end + lcd.drawText(1, 0, "Got a rudder?", 0) + lcd.drawFilledRectangle(0, 0, LCD_W, 8, FILL_WHITE) + lcd.drawCombobox(0, 8, LCD_W, rudderModeItems, rudderMode, getFieldFlags(0)) +end + +local function rudderMenu(event) + if dirty then + dirty = false + drawRudderMenu() + end + + navigate(event, fieldsMax, page-1, page+1) + + if field==0 then + rudderMode = fieldIncDec(event, rudderMode, 1) + elseif field==1 then + rudCH1 = channelIncDec(event, rudCH1) + end +end + +-- Servo (limits) Menu +local function drawServoMenu(limits) + lcd.clear() + lcd.drawSource(1, 0, MIXSRC_CH1+servoPage, 0) + lcd.drawText(25, 0, "servo min/max/center/direction?", 0) + lcd.drawFilledRectangle(0, 0, LCD_W, 8, FILL_WHITE) + lcd.drawText(LCD_W/2-19, LCD_H-8, ">>>", 0); + lcd.drawNumber(140, 35, limits.min, PREC1+getFieldFlags(0)); + lcd.drawNumber(205, 35, limits.max, PREC1+getFieldFlags(1)); + lcd.drawNumber(170, 9, limits.offset, PREC1+getFieldFlags(2)); + if limits.revert == 0 then + lcd.drawText(129, 50, "\126", getFieldFlags(3)); + else + lcd.drawText(129, 50, "\127", getFieldFlags(3)); + end + fieldsMax = 3 +end + +local function servoMenu(event) + local limits = model.getOutput(servoPage) + + if dirty then + dirty = false + drawServoMenu(limits) + end + + navigate(event, fieldsMax, page, page) + + if edit then + if field==0 then + limits.min = valueIncDec(event, limits.min, -1000, 0) + elseif field==1 then + limits.max = valueIncDec(event, limits.max, 0, 1000) + elseif field==2 then + limits.offset = valueIncDec(event, limits.offset, -1000, 1000) + elseif field==3 then + limits.revert = fieldIncDec(event, limits.revert, 1) + end + model.setOutput(servoPage, limits) + elseif event == EVT_EXIT_BREAK then + servoPage = nil + dirty = true + end +end + +-- Confirmation Menu +local function addMix(channel, input, name, weight, index) + local mix = { source=input, name=name } + if weight ~= nil then + mix.weight = weight + end + if index == nil then + index = 0 + end + model.insertMix(channel, index, mix) +end + +local function applySettings() + model.defaultInputs() + model.deleteMixes() + if engineMode == 1 then + addMix(thrCH1, MIXSRC_FIRST_INPUT+defaultChannel(2), "Engine") + end + addMix(elevCH1, MIXSRC_FIRST_INPUT+defaultChannel(1), "D-EleL", 50) + addMix(elevCH1, MIXSRC_FIRST_INPUT+defaultChannel(3), "D-AilL", 50, 1) + addMix(elevCH2, MIXSRC_FIRST_INPUT+defaultChannel(1), "D-EleR", 50) + addMix(elevCH2, MIXSRC_FIRST_INPUT+defaultChannel(3), "D-AilR", -50, 1) + if rudderMode == 1 then + addMix(rudCH1, MIXSRC_FIRST_INPUT+defaultChannel(0), "Rudder") + end +end + +local function drawNextLine(x, y, label, channel) + lcd.drawText(x, y, label, 0); + lcd.drawSource(x+52, y, MIXSRC_CH1+channel, 0) + y = y + 8 + if y > 50 then + y = 12 + x = 120 + end + return x, y +end + +local function drawConfirmationMenu() + local x = 22 + local y = 12 + lcd.clear() + lcd.drawText(48, 1, "Ready to go?", 0); + lcd.drawFilledRectangle(0, 0, LCD_W, 9, 0) + if engineMode == 1 then + x, y = drawNextLine(x, y, "Thr:", thrCH1) + end + x, y = drawNextLine(x, y, "Ele L:", elevCH1) + x, y = drawNextLine(x, y, "Ele R:", elevCH2) + if rudderMode == 1 then + drawNextLine(x, y, "Rudder:", rudCH1) + end + lcd.drawText(48, LCD_H-8, "[Enter Long] to confirm", 0); + lcd.drawFilledRectangle(0, LCD_H-9, LCD_W, 9, 0) + fieldsMax = 0 +end + +local function confirmationMenu(event) + if dirty then + dirty = false + drawConfirmationMenu() + end + + navigate(event, fieldsMax, RUDDER_PAGE, page) + + if event == EVT_EXIT_BREAK then + return 2 + elseif event == EVT_ENTER_LONG then + killEvents(event) + applySettings() + return 2 + else + return 0 + end +end + +-- Main + +local function run(event) + if event == nil then + error("Cannot be run as a model script!") + end + + if servoPage ~= nil then + servoMenu(event) + elseif page == ENGINE_PAGE then + engineMenu(event) + elseif page == ELEVONS_PAGE then + elevonsMenu(event) + elseif page == RUDDER_PAGE then + rudderMenu(event) + elseif page == CONFIRMATION_PAGE then + return confirmationMenu(event) + end + return 0 +end + +return { init=init, run=run } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x7/SCRIPTS/WIZARD/multi.lua opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x7/SCRIPTS/WIZARD/multi.lua --- opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x7/SCRIPTS/WIZARD/multi.lua 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x7/SCRIPTS/WIZARD/multi.lua 2017-12-17 16:22:27.000000000 +0000 @@ -0,0 +1,308 @@ +---- ######################################################################### +---- # # +---- # Copyright (C) OpenTX # +-----# # +---- # License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html # +---- # # +---- # This program is free software; you can redistribute it and/or modify # +---- # it under the terms of the GNU General Public License version 2 as # +---- # published by the Free Software Foundation. # +---- # # +---- # 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. # +---- # # +---- ######################################################################### +-- Multicopter Wizard pages +local THROTTLE_PAGE = 0 +local ROLL_PAGE = 1 +local PITCH_PAGE = 2 +local YAW_PAGE = 3 +local CONFIRMATION_PAGE = 4 + +-- Navigation variables +local page = THROTTLE_PAGE +local dirty = true +local edit = false +local field = 0 +local fieldsMax = 0 +local comboBoxMode = 0 -- Scrap variable + +-- Model settings +local thrCH1 = 0 +local rollCH1 = 0 +local yawCH1 = 0 +local pitchCH1 = 0 + +-- Common functions +local lastBlink = 0 +local function blinkChanged() + local time = getTime() % 128 + local blink = (time - time % 64) / 64 + if blink ~= lastBlink then + lastBlink = blink + return true + else + return false + end +end + +local function fieldIncDec(event, value, max, force) + if edit or force==true then + if event == EVT_ROT_RIGHT then + value = (value + max) + dirty = true + elseif event == EVT_ROT_LEFT then + value = (value + max + 2) + dirty = true + end + value = (value % (max+1)) + end + return value +end + +local function valueIncDec(event, value, min, max) + if edit then + if event == EVT_ROT_RIGHT or event == EVT_ROT_RIGHT then + if value < max then + value = (value + 1) + dirty = true + end + elseif event == EVT_ROT_LEFT or event == EVT_ROT_LEFT then + if value > min then + value = (value - 1) + dirty = true + end + end + end + return value +end + +local function navigate(event, fieldMax, prevPage, nextPage) + if event == EVT_ENTER_BREAK then + edit = not edit + dirty = true + elseif edit then + if event == EVT_EXIT_BREAK then + edit = false + dirty = true + elseif not dirty then + dirty = blinkChanged() + end + else + if event == EVT_PAGE_BREAK then + page = nextPage + field = 0 + dirty = true + elseif event == EVT_PAGE_LONG then + page = prevPage + field = 0 + killEvents(event); + dirty = true + else + field = fieldIncDec(event, field, fieldMax, true) + end + end +end + +local function getFieldFlags(position) + flags = 0 + if field == position then + flags = INVERS + if edit then + flags = INVERS + BLINK + end + end + return flags +end + +local function channelIncDec(event, value) + if not edit and event==EVT_MENU_BREAK then + servoPage = value + dirty = true + else + value = valueIncDec(event, value, 0, 15) + end + return value +end + +-- Init function +local function init() + thrCH1 = defaultChannel(2) + rollCH1 = defaultChannel(3) + yawCH1 = defaultChannel(0) + pitchCH1 = defaultChannel(1) +end + +-- Throttle Menu +local function drawThrottleMenu() + lcd.clear() + lcd.drawText(1, 0, "Multicopter", 0) + lcd.drawFilledRectangle(0, 0, LCD_W, 8, FILL_WHITE) + lcd.drawCombobox(0, 8, LCD_W, {"Throttle"}, comboBoxMode, getFieldFlags(1)) + lcd.drawText(5, 30, "Assign channel", 0); + lcd.drawText(5, 40, ">>>", 0); + lcd.drawSource(25, 40, MIXSRC_CH1+thrCH1, getFieldFlags(0)) + fieldsMax = 0 +end + +local function throttleMenu(event) + if dirty then + dirty = false + drawThrottleMenu() + end + navigate(event, fieldsMax, page, page+1) + thrCH1 = channelIncDec(event, thrCH1) +end + +-- Roll Menu +local function drawRollMenu() + lcd.clear() + lcd.drawText(1, 0, "Multicopter", 0) + lcd.drawFilledRectangle(0, 0, LCD_W, 8, FILL_WHITE) + lcd.drawCombobox(0, 8, LCD_W, {"Roll"}, comboBoxMode, getFieldFlags(1)) + lcd.drawText(5, 30, "Assign channel", 0); + lcd.drawText(5, 40, ">>>", 0); + lcd.drawSource(25, 40, MIXSRC_CH1+rollCH1, getFieldFlags(0)) + fieldsMax = 0 +end + +local function rollMenu(event) + if dirty then + dirty = false + drawRollMenu() + end + navigate(event, fieldsMax, page-1, page+1) + rollCH1 = channelIncDec(event, rollCH1) +end + +-- Pitch Menu +local function drawPitchMenu() + lcd.clear() + lcd.drawText(1, 0, "Multicopter", 0) + lcd.drawFilledRectangle(0, 0, LCD_W, 8, FILL_WHITE) + lcd.drawCombobox(0, 8, LCD_W, {"Pitch"}, comboBoxMode, getFieldFlags(1)) + lcd.drawText(5, 30, "Assign channel", 0); + lcd.drawText(5, 40, ">>>", 0); + lcd.drawSource(25, 40, MIXSRC_CH1+pitchCH1, getFieldFlags(0)) + fieldsMax = 0 +end + +local function pitchMenu(event) + if dirty then + dirty = false + drawPitchMenu() + end + navigate(event, fieldsMax, page-1, page+1) + pitchCH1 = channelIncDec(event, pitchCH1) +end + +-- Yaw Menu +local function drawYawMenu() + lcd.clear() + lcd.drawText(1, 0, "Multicopter", 0) + lcd.drawFilledRectangle(0, 0, LCD_W, 8, FILL_WHITE) + lcd.drawCombobox(0, 8, LCD_W, {"Yaw"}, comboBoxMode, getFieldFlags(1)) + lcd.drawText(5, 30, "Assign channel", 0); + lcd.drawText(5, 40, ">>>", 0); + lcd.drawSource(25, 40, MIXSRC_CH1+yawCH1, getFieldFlags(0)) + fieldsMax = 0 +end + +local function yawMenu(event) + if dirty then + dirty = false + drawYawMenu() + end + navigate(event, fieldsMax, page-1, page+1) + yawCH1 = channelIncDec(event, yawCH1) +end + +-- Confirmation Menu +local function drawNextLine(x, y, label, channel) + lcd.drawText(x, y, label, 0); + lcd.drawSource(x+52, y, MIXSRC_CH1+channel, 0) + y = y + 8 + if y > 50 then + y = 12 + x = 120 + end + return x, y +end + +local function drawConfirmationMenu() + local x = 22 + local y = 12 + lcd.clear() + lcd.drawText(0, 1, "Ready to go?", 0); + lcd.drawFilledRectangle(0, 0, LCD_W, 9, 0) + x, y = drawNextLine(x, y, "Throttle", thrCH1) + x, y = drawNextLine(x, y, "Roll", rollCH1) + x, y = drawNextLine(x, y, "Pitch", pitchCH1) + x, y = drawNextLine(x, y, "Yaw", yawCH1) + lcd.drawText(0, LCD_H-8, "[Enter Long] to confirm", 0); + lcd.drawFilledRectangle(0, LCD_H-9, LCD_W, 9, 0) + fieldsMax = 0 +end + +local function addMix(channel, input, name, weight, index) + local mix = { source=input, name=name } + if weight ~= nil then + mix.weight = weight + end + if index == nil then + index = 0 + end + model.insertMix(channel, index, mix) +end + +local function applySettings() + model.defaultInputs() + model.deleteMixes() + addMix(thrCH1, MIXSRC_FIRST_INPUT+defaultChannel(2), "Engine") + addMix(rollCH1, MIXSRC_FIRST_INPUT+defaultChannel(3), "Roll") + addMix(yawCH1, MIXSRC_FIRST_INPUT+defaultChannel(0), "Yaw") + addMix(pitchCH1, MIXSRC_FIRST_INPUT+defaultChannel(1), "Pitch") +end + +local function confirmationMenu(event) + if dirty then + dirty = false + drawConfirmationMenu() + end + + navigate(event, fieldsMax, YAW_PAGE, page) + + if event == EVT_EXIT_BREAK then + return 2 + elseif event == EVT_ENTER_LONG then + killEvents(event) + applySettings() + return 2 + else + return 0 + end +end + +-- Main +local function run(event) + if event == nil then + error("Cannot be run as a model script!") + end + + if page == THROTTLE_PAGE then + throttleMenu(event) + elseif page == ROLL_PAGE then + rollMenu(event) + elseif page == YAW_PAGE then + yawMenu(event) + elseif page == PITCH_PAGE then + pitchMenu(event) + elseif page == CONFIRMATION_PAGE then + return confirmationMenu(event) + end + return 0 +end + +return { init=init, run=run } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x7/SCRIPTS/WIZARD/plane.lua opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x7/SCRIPTS/WIZARD/plane.lua --- opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x7/SCRIPTS/WIZARD/plane.lua 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x7/SCRIPTS/WIZARD/plane.lua 2017-12-17 16:22:27.000000000 +0000 @@ -0,0 +1,581 @@ +---- ######################################################################### +---- # # +---- # Copyright (C) OpenTX # +-----# # +---- # License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html # +---- # # +---- # This program is free software; you can redistribute it and/or modify # +---- # it under the terms of the GNU General Public License version 2 as # +---- # published by the Free Software Foundation. # +---- # # +---- # 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. # +---- # # +---- ######################################################################### +-- Plane Wizard pages +local ENGINE_PAGE = 0 +local AILERONS_PAGE = 1 +local FLAPERONS_PAGE = 2 +local BRAKES_PAGE = 3 +local TAIL_PAGE = 4 +local CONFIRMATION_PAGE = 5 + +-- Navigation variables +local page = ENGINE_PAGE +local dirty = true +local edit = false +local field = 0 +local fieldsMax = 0 + +-- Model settings +local engineMode = 1 +local thrCH1 = 0 +local aileronsMode = 1 +local ailCH1 = 0 +local ailCH2 = 5 +local flapsMode = 0 +local flapsCH1 = 6 +local flapsCH2 = 7 +local brakesMode = 0 +local brakesCH1 = 8 +local brakesCH2 = 9 +local tailMode = 1 +local eleCH1 = 0 +local eleCH2 = 4 +local rudCH1 = 0 +local servoPage = nil + +-- Common functions +local lastBlink = 0 +local function blinkChanged() + local time = getTime() % 128 + local blink = (time - time % 64) / 64 + if blink ~= lastBlink then + lastBlink = blink + return true + else + return false + end +end + +local function fieldIncDec(event, value, max, force) + if edit or force==true then + if event == EVT_ROT_LEFT then + value = (value + max) + dirty = true + elseif event == EVT_ROT_RIGHT then + value = (value + max + 2) + dirty = true + end + value = (value % (max+1)) + end + return value +end + +local function valueIncDec(event, value, min, max) + if edit then + if event == EVT_ROT_LEFT or event == EVT_ROT_LEFT then + if value < max then + value = (value + 1) + dirty = true + end + elseif event == EVT_ROT_RIGHT or event == EVT_ROT_RIGHT then + if value > min then + value = (value - 1) + dirty = true + end + end + end + return value +end + +local function navigate(event, fieldMax, prevPage, nextPage) + if event == EVT_ENTER_BREAK then + edit = not edit + dirty = true + elseif edit then + if event == EVT_EXIT_BREAK then + edit = false + dirty = true + elseif not dirty then + dirty = blinkChanged() + end + else + if event == EVT_PAGE_BREAK then + page = nextPage + field = 0 + dirty = true + elseif event == EVT_PAGE_LONG then + page = prevPage + field = 0 + killEvents(event); + dirty = true + else + field = fieldIncDec(event, field, fieldMax, true) + end + end +end + +local function getFieldFlags(position) + flags = 0 + if field == position then + flags = INVERS + if edit then + flags = INVERS + BLINK + end + end + return flags +end + +local function channelIncDec(event, value) + if not edit and event==EVT_MENU_BREAK then + servoPage = value + dirty = true + else + value = valueIncDec(event, value, 0, 15) + end + return value +end + +-- Init function +local function init() + rudCH1 = defaultChannel(0) + eleCH1 = defaultChannel(1) + thrCH1 = defaultChannel(2) + ailCH1 = defaultChannel(3) +end + +-- Engine Menu +local engineModeItems = {"No", "Yes"} +local function drawEngineMenu() + lcd.clear() + if engineMode == 1 then + -- 1 channel + lcd.drawText(5, 30, "Assign channel", 0); + lcd.drawText(5, 40, ">>>", 0); + lcd.drawSource(25, 40, MIXSRC_CH1+thrCH1, getFieldFlags(1)) + fieldsMax = 1 + else + -- No engine + fieldsMax = 0 + end + lcd.drawText(1, 0, "Got an engine?", 0) + lcd.drawFilledRectangle(0, 0, LCD_W, 8, FILL_WHITE) + lcd.drawCombobox(0, 8, LCD_W, engineModeItems, engineMode, getFieldFlags(0)) +end + +local function engineMenu(event) + if dirty then + dirty = false + drawEngineMenu() + end + + navigate(event, fieldsMax, page, page+1) + + if field==0 then + engineMode = fieldIncDec(event, engineMode, 1) + elseif field==1 then + thrCH1 = channelIncDec(event, thrCH1) + end +end + +-- Ailerons Menu +local aileronsModeItems = {"No", "Yes, 1 channel", "Yes, 2 channels"} +local function drawAileronsMenu() + lcd.clear() + if aileronsMode == 2 then + -- 2 channels + lcd.drawText(5, 30, "Assign channels", 0); + lcd.drawText(30, 40, "L", 0); + lcd.drawText(65, 40, "R", 0); + lcd.drawText(5, 50, ">>>", 0); + lcd.drawSource(25, 50, MIXSRC_CH1+ailCH1, getFieldFlags(1)) + lcd.drawSource(60, 50, MIXSRC_CH1+ailCH2, getFieldFlags(2)) + fieldsMax = 2 + elseif aileronsMode == 1 then + -- 1 channel + lcd.drawText(5, 30, "Assign channel", 0); + lcd.drawText(5, 40, ">>>", 0); + lcd.drawSource(25, 40, MIXSRC_CH1+ailCH1, getFieldFlags(1)) + fieldsMax = 1 + else + -- No ailerons + fieldsMax = 0 + end + lcd.drawText(1, 0, "Got ailerons?", 0) + lcd.drawFilledRectangle(0, 0, LCD_W, 8, FILL_WHITE) + lcd.drawCombobox(0, 8, LCD_W, aileronsModeItems, aileronsMode, getFieldFlags(0)) +end + +local function aileronsMenu(event) + if dirty then + dirty = false + drawAileronsMenu() + end + + navigate(event, fieldsMax, page-1, page+1) + + if field==0 then + aileronsMode = fieldIncDec(event, aileronsMode, 2) + elseif field==1 then + ailCH1 = channelIncDec(event, ailCH1) + elseif field==2 then + ailCH2 = channelIncDec(event, ailCH2) + end +end + +-- Flaps Menu +local flapsModeItems = {"No", "Yes, 1 channel", "Yes, 2 channels"} +local function drawFlapsMenu() + lcd.clear() + if flapsMode == 0 then + -- no flaps + fieldsMax = 0 + elseif flapsMode == 1 then + -- 1 channel + lcd.drawText(5, 30, "Assign channel", 0); + lcd.drawText(5, 40, ">>>", 0); + lcd.drawSource(25, 40, MIXSRC_CH1+flapsCH1, getFieldFlags(1)) + fieldsMax = 1 + elseif flapsMode == 2 then + -- 2 channels + lcd.drawText(5, 30, "Assign channels", 0); + lcd.drawText(30, 40, "L", 0); + lcd.drawText(65, 40, "R", 0); + lcd.drawText(5, 50, ">>>", 0); + lcd.drawSource(25, 50, MIXSRC_CH1+flapsCH1, getFieldFlags(1)) + lcd.drawSource(60, 50, MIXSRC_CH1+flapsCH2, getFieldFlags(2)) + fieldsMax = 2 + end + lcd.drawText(1, 0, "Got flaps?", 0) + lcd.drawFilledRectangle(0, 0, LCD_W, 8, FILL_WHITE) + lcd.drawCombobox(0, 8, LCD_W, flapsModeItems, flapsMode, getFieldFlags(0)) +end + +local function flapsMenu(event) + if dirty then + dirty = false + drawFlapsMenu() + end + + navigate(event, fieldsMax, page-1, page+1) + + if field==0 then + flapsMode = fieldIncDec(event, flapsMode, 2) + elseif field==1 then + flapsCH1 = channelIncDec(event, flapsCH1) + elseif field==2 then + flapsCH2 = channelIncDec(event, flapsCH2) + end +end + +-- Airbrakes Menu +local brakesModeItems = {"No", "Yes, 1 channel", "Yes, 2 channels"} +local function drawBrakesMenu() + lcd.clear() + if brakesMode == 0 then + -- no brakes + fieldsMax = 0 + elseif brakesMode == 1 then + -- 1 channel + lcd.drawText(5, 30, "Assign channel", 0); + lcd.drawText(5, 40, ">>>", 0); + lcd.drawSource(25, 40, MIXSRC_CH1+brakesCH1, getFieldFlags(1)) + fieldsMax = 1 + elseif brakesMode == 2 then + -- 2 channels + lcd.drawText(5, 30, "Assign channels", 0); + lcd.drawText(30, 40, "L", 0); + lcd.drawText(65, 40, "R", 0); + lcd.drawText(5, 50, ">>>", 0); + lcd.drawSource(25, 50, MIXSRC_CH1+brakesCH1, getFieldFlags(1)) + lcd.drawSource(60, 50, MIXSRC_CH1+brakesCH2, getFieldFlags(2)) + fieldsMax = 2 + end + lcd.drawText(1, 0, "Got air brakes?", 0) + lcd.drawFilledRectangle(0, 0, LCD_W, 8, FILL_WHITE) + lcd.drawCombobox(0, 8, LCD_W, brakesModeItems, brakesMode, getFieldFlags(0)) +end + +local function brakesMenu(event) + if dirty then + dirty = false + drawBrakesMenu() + end + + navigate(event, fieldsMax, page-1, page+1) + + if field==0 then + brakesMode = fieldIncDec(event, brakesMode, 2) + elseif field==1 then + brakesCH1 = channelIncDec(event, brakesCH1) + elseif field==2 then + brakesCH2 = channelIncDec(event, brakesCH2) + end +end + +-- Tail Menu +local tailModeItems = {"Ele(1)", "Ele(1) + Ruder(1)", "Ele(2) + Ruder(1)", "V-Tail(2)"} +local function drawTailMenu() + lcd.clear() + if tailMode == 0 then + -- Elevator(1ch), no rudder... + lcd.drawText(5, 30, "Assign channel", 0); + lcd.drawText(5, 40, ">>>", 0); + lcd.drawSource(25, 40, MIXSRC_CH1+eleCH1, getFieldFlags(1)) + fieldsMax = 1 + elseif tailMode == 1 then + -- Elevator(1ch) + rudder... + lcd.drawText(5, 30, "Assign channels", 0); + lcd.drawText(25, 40, "Ele", 0); + lcd.drawText(60, 40, "Rud", 0); + lcd.drawText(5, 50, ">>>", 0); + lcd.drawSource(25, 50, MIXSRC_CH1+eleCH1, getFieldFlags(1)) + lcd.drawSource(60, 50, MIXSRC_CH1+rudCH1, getFieldFlags(2)) + fieldsMax = 2 + elseif tailMode == 2 then + -- Elevator(2ch) + rudder... + lcd.drawText(5, 30, "Assign channels", 0); + lcd.drawText(25, 40, "EleL", 0); + lcd.drawText(60, 40, "EleR", 0); + lcd.drawText(95, 40, "Rud", 0); + lcd.drawText(5, 50, ">>>", 0); + lcd.drawSource(25, 50, MIXSRC_CH1+eleCH1, getFieldFlags(1)) + lcd.drawSource(60, 50, MIXSRC_CH1+eleCH2, getFieldFlags(2)) + lcd.drawSource(95, 50, MIXSRC_CH1+rudCH1, getFieldFlags(3)) + fieldsMax = 3 + else + -- V-Tail... + lcd.drawText(5, 30, "Assign channels", 0); + lcd.drawText(25, 40, "VtaL", 0); + lcd.drawText(60, 40, "VtaR", 0); + lcd.drawText(5, 50, ">>>", 0); + lcd.drawSource(25, 50, MIXSRC_CH1+eleCH1, getFieldFlags(1)) + lcd.drawSource(60, 50, MIXSRC_CH1+eleCH2, getFieldFlags(2)) + fieldsMax = 2 + end + lcd.drawText(1, 0, "Tail config", 0) + lcd.drawFilledRectangle(0, 0, LCD_W, 8, FILL_WHITE) + lcd.drawCombobox(0, 8, LCD_W, tailModeItems, tailMode, getFieldFlags(0)) +end + +local function tailMenu(event) + if dirty then + dirty = false + drawTailMenu() + end + + navigate(event, fieldsMax, page-1, page+1) + + if field==0 then + tailMode = fieldIncDec(event, tailMode, 3) + elseif field==1 then + eleCH1 = channelIncDec(event, eleCH1) + elseif (field==2 and tailMode==1) or field==3 then + rudCH1 = channelIncDec(event, rudCH1) + elseif field==2 then + eleCH2 = channelIncDec(event, eleCH2) + end +end + +-- Servo (limits) Menu +local function drawServoMenu(limits) + lcd.clear() + lcd.drawSource(1, 0, MIXSRC_CH1+servoPage, 0) + lcd.drawText(25, 0, "servo min/max/center/direction?", 0) + lcd.drawFilledRectangle(0, 0, LCD_W, 8, FILL_WHITE) + lcd.drawLine(LCD_W/2-1, 8, LCD_W/2-1, LCD_H, DOTTED, 0) + lcd.drawText(LCD_W/2-19, LCD_H-8, ">>>", 0); + lcd.drawNumber(140, 35, limits.min, PREC1+getFieldFlags(0)); + lcd.drawNumber(205, 35, limits.max, PREC1+getFieldFlags(1)); + lcd.drawNumber(170, 9, limits.offset, PREC1+getFieldFlags(2)); + if limits.revert == 0 then + lcd.drawText(129, 50, "\126", getFieldFlags(3)); + else + lcd.drawText(129, 50, "\127", getFieldFlags(3)); + end + fieldsMax = 3 +end + +local function servoMenu(event) + local limits = model.getOutput(servoPage) + + if dirty then + dirty = false + drawServoMenu(limits) + end + + navigate(event, fieldsMax, page, page) + + if edit then + if field==0 then + limits.min = valueIncDec(event, limits.min, -1000, 0) + elseif field==1 then + limits.max = valueIncDec(event, limits.max, 0, 1000) + elseif field==2 then + limits.offset = valueIncDec(event, limits.offset, -1000, 1000) + elseif field==3 then + limits.revert = fieldIncDec(event, limits.revert, 1) + end + model.setOutput(servoPage, limits) + elseif event == EVT_EXIT_BREAK then + servoPage = nil + dirty = true + end +end + +-- Confirmation Menu +local function drawNextLine(x, y, label, channel) + lcd.drawText(x, y, label, 0); + lcd.drawSource(x+30, y, MIXSRC_CH1+channel, 0) + y = y + 8 + if y > 50 then + y = 12 + x = 70 + end + return x, y +end + +local function drawConfirmationMenu() + local x = 5 + local y = 12 + lcd.clear() + lcd.drawText(0, 1, "Ready to go?", 0); + lcd.drawFilledRectangle(0, 0, LCD_W, 9, 0) + if engineMode == 1 then + x, y = drawNextLine(x, y, "Thr", thrCH1) + end + if aileronsMode == 1 then + x, y = drawNextLine(x, y, "Ail", ailCH1) + elseif aileronsMode == 2 then + x, y = drawNextLine(x, y, "AilL", ailCH1) + x, y = drawNextLine(x, y, "AilR", ailCH2) + end + if flapsMode == 1 then + x, y = drawNextLine(x, y, "Flap", flapsCH1) + elseif flapsMode == 2 then + x, y = drawNextLine(x, y, "FlpL", flapsCH1) + x, y = drawNextLine(x, y, "FlpR", flapsCH2) + end + if brakesMode == 1 then + x, y = drawNextLine(x, y, "Brak", brakesCH1) + elseif brakesMode == 2 then + x, y = drawNextLine(x, y, "BrkL", brakesCH1) + x, y = drawNextLine(x, y, "BrkR", brakesCH2) + end + if tailMode == 3 then + x, y = drawNextLine(x, y, "VtaL", eleCH1) + x, y = drawNextLine(x, y, "VtaR", eleCH2) + else + x, y = drawNextLine(x, y, "Rud", rudCH1) + if tailMode == 1 then + x, y = drawNextLine(x, y, "Elev", eleCH1) + elseif tailMode == 2 then + x, y = drawNextLine(x, y, "EleL", eleCH1) + x, y = drawNextLine(x, y, "EleR", eleCH2) + end + end + lcd.drawText(0, LCD_H-8, "[Enter Long] to confirm", 0); + lcd.drawFilledRectangle(0, LCD_H-9, LCD_W, 9, 0) + fieldsMax = 0 +end + +local function addMix(channel, input, name, weight, index) + local mix = { source=input, name=name } + if weight ~= nil then + mix.weight = weight + end + if index == nil then + index = 0 + end + model.insertMix(channel, index, mix) +end + +local function applySettings() + model.defaultInputs() + model.deleteMixes() + if engineMode > 0 then + addMix(thrCH1, MIXSRC_FIRST_INPUT+defaultChannel(2), "Engine") + end + if aileronsMode == 1 then + addMix(ailCH1, MIXSRC_FIRST_INPUT+defaultChannel(3), "Ail") + elseif aileronsMode == 2 then + addMix(ailCH1, MIXSRC_FIRST_INPUT+defaultChannel(3), "AilL") + addMix(ailCH2, MIXSRC_FIRST_INPUT+defaultChannel(3), "AilR", -100) + end + if flapsMode == 1 then + addMix(flapsCH1, MIXSRC_SA, "Flap") + elseif flapsMode == 2 then + addMix(flapsCH1, MIXSRC_SA, "FlapL") + addMix(flapsCH2, MIXSRC_SA, "FlapR") + end + if brakesMode == 1 then + addMix(brakesCH1, MIXSRC_SD, "Brake") + elseif brakesMode == 2 then + addMix(brakesCH1, MIXSRC_SD, "BrakeL") + addMix(brakesCH2, MIXSRC_SD, "BrakeR") + end + if tailMode == 3 then + addMix(eleCH1, MIXSRC_FIRST_INPUT+defaultChannel(1), "V-EleL", 50) + addMix(eleCH1, MIXSRC_FIRST_INPUT+defaultChannel(0), "V-RudL", 50, 1) + addMix(eleCH2, MIXSRC_FIRST_INPUT+defaultChannel(1), "V-EleR", 50) + addMix(eleCH2, MIXSRC_FIRST_INPUT+defaultChannel(0), "V-RudR", -50, 1) + else + if tailMode > 0 then + addMix(rudCH1, MIXSRC_FIRST_INPUT+defaultChannel(0), "Rudder") + end + if tailMode == 1 then + addMix(eleCH1, MIXSRC_FIRST_INPUT+defaultChannel(1), "Elev") + elseif tailMode == 2 then + addMix(eleCH1, MIXSRC_FIRST_INPUT+defaultChannel(1), "ElevG") + addMix(eleCH2, MIXSRC_FIRST_INPUT+defaultChannel(1), "ElevD") + end + end +end + +local function confirmationMenu(event) + if dirty then + dirty = false + drawConfirmationMenu() + end + + navigate(event, fieldsMax, TAIL_PAGE, page) + + if event == EVT_EXIT_BREAK then + return 2 + elseif event == EVT_ENTER_LONG then + killEvents(event) + applySettings() + return 2 + else + return 0 + end +end + +-- Main +local function run(event) + if event == nil then + error("Cannot be run as a model script!") + end + + if servoPage ~= nil then + servoMenu(event) + elseif page == ENGINE_PAGE then + engineMenu(event) + elseif page == AILERONS_PAGE then + aileronsMenu(event) + elseif page == FLAPERONS_PAGE then + flapsMenu(event) + elseif page == BRAKES_PAGE then + brakesMenu(event) + elseif page == TAIL_PAGE then + tailMenu(event) + elseif page == CONFIRMATION_PAGE then + return confirmationMenu(event) + end + return 0 +end + +return { init=init, run=run } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x7/SCRIPTS/WIZARD/wizard.lua opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x7/SCRIPTS/WIZARD/wizard.lua --- opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x7/SCRIPTS/WIZARD/wizard.lua 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x7/SCRIPTS/WIZARD/wizard.lua 2017-12-17 16:22:27.000000000 +0000 @@ -0,0 +1,92 @@ +---- ######################################################################### +---- # # +---- # Copyright (C) OpenTX # +-----# # +---- # License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html # +---- # # +---- # This program is free software; you can redistribute it and/or modify # +---- # it under the terms of the GNU General Public License version 2 as # +---- # published by the Free Software Foundation. # +---- # # +---- # 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. # +---- # # +---- ######################################################################### +-- Navigation variables +local dirty = true + +-- Model types +local modelType = 0 +local MODELTYPE_PLANE = 0 +local MODELTYPE_DELTA = 1 +local MODELTYPE_QUAD = 2 + +-- Common functions +local function fieldIncDec(event, value, max) + if event == EVT_ROT_LEFT then + value = (value + max) + dirty = true + elseif event == EVT_ROT_RIGHT then + value = (value + max + 2) + dirty = true + end + value = (value % (max+1)) + return value +end + +-- Model Type Menu +local function modelTypeSurround(index) + if(index<=1) then + lcd.drawFilledRectangle(59*(index%2)+12, 13, 43, 23) + else + lcd.drawFilledRectangle(59*(index%2)+12, 34, 40, 20) + end +end + +local function drawModelChoiceMenu() + lcd.clear() + lcd.drawScreenTitle("Select model type", 0, 0) + lcd.drawText( 20, 20, "Plane") + lcd.drawText( 78, 20, "Delta") + lcd.drawText( 20, 40, "Multi") + modelTypeSurround(modelType) + fieldsMax = 0 +end + +local function modelTypeMenu(event) + if dirty == true then + drawModelChoiceMenu() + dirty = false + end + if event == EVT_ENTER_BREAK then + if modelType == MODELTYPE_PLANE then + return "plane.lua" + elseif modelType == MODELTYPE_DELTA then + return "delta.lua" + elseif modelType == MODELTYPE_QUAD then + return "multi.lua" + end + dirty = true + else + modelType = fieldIncDec(event, modelType, 2) + end + return 0 +end + +-- Main +local function run(event) + if event == nil then + error("Cannot be run as a model script!") + end + + if event == EVT_EXIT_BREAK then + return 2 + end + + + return modelTypeMenu(event) +end + +return { run=run } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x7/SxR/SxR_Calibrate.lua opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x7/SxR/SxR_Calibrate.lua --- opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x7/SxR/SxR_Calibrate.lua 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x7/SxR/SxR_Calibrate.lua 2017-11-11 11:29:14.000000000 +0000 @@ -0,0 +1,299 @@ +---- ######################################################################### +---- # # +---- # Copyright (C) OpenTX # +-----# # +---- # License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html # +---- # # +---- # This program is free software; you can redistribute it and/or modify # +---- # it under the terms of the GNU General Public License version 2 as # +---- # published by the Free Software Foundation. # +---- # # +---- # 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. # +---- # # +---- ######################################################################### +local VALUE = 0 +local COMBO = 1 + +local COLUMN_2 = 150 + +local edit = false +local page = 1 +local current = 1 +local refreshState = 0 +local refreshIndex = 0 +local calibrationState = 0 +local pageOffset = 0 +local calibrationStep = 0 +local pages = {} +local fields = {} +local modifications = {} +local positionConfirmed = 0 +local orientationAutoSense = 0 + +local calibrationFields = { + {"X:", VALUE, 0x9E, 0, -100, 100, "%"}, + {"Y:", VALUE, 0x9F, 0, -100, 100, "%"}, + {"Z:", VALUE, 0xA0, 0, -100, 100, "%"} +} + +local function drawProgressBar() + local width = (140 * refreshIndex) / #fields + lcd.drawRectangle(30, 1, 144, 6) + lcd.drawFilledRectangle(32, 3, width, 2); +end + +-- Select the next or previous page +local function selectPage(step) + page = 1 + ((page + step - 1 + #pages) % #pages) + refreshIndex = 0 + calibrationStep = 0 + pageOffset = 0 +end + +-- Draw initial warning page +local function runWarningPage(event) + lcd.clear() + lcd.drawScreenTitle("SxR Calibration", page, #pages) + lcd.drawText(0, 10, "You only need to calibrate", SMLSIZE) + lcd.drawText(0, 20, "once. You will need the SxR,", SMLSIZE) + lcd.drawText(0, 30, "power, and a level surface.", SMLSIZE) + lcd.drawText(0, 40, "Press [Enter] when ready", SMLSIZE) + lcd.drawText(0, 50, "Press [Exit] to cancel", SMLSIZE) + if event == EVT_ENTER_BREAK then + selectPage(1) + return 0 + elseif event == EVT_EXIT_BREAK then + return 2 + end + return 0 +end + +-- Redraw the current page +local function redrawFieldsPage() + lcd.clear() + lcd.drawScreenTitle("SxR Calibration", page, #pages) + + if refreshIndex < #fields then + drawProgressBar() + end + + for index = 1, 7, 1 do + local field = fields[pageOffset+index] + if field == nil then + break + end + + local attr = current == (pageOffset+index) and ((edit == true and BLINK or 0) + INVERS) or 0 + + lcd.drawText(0, 1+8*index, field[1]) + + if field[4] == nil then + lcd.drawText(COLUMN_2, 1+8*index, "---", attr) + else + if field[2] == VALUE then + lcd.drawNumber(COLUMN_2, 1+8*index, field[4], LEFT + attr) + elseif field[2] == COMBO then + if field[4] >= 0 and field[4] < #(field[5]) then + lcd.drawText(COLUMN_2, 1+8*index, field[5][1+field[4]], attr) + end + end + end + end +end + +local function telemetryRead(field) + return sportTelemetryPush(0x17, 0x30, 0x0C30, field) +end + +local function telemetryWrite(field, value) + return sportTelemetryPush(0x17, 0x31, 0x0C30, field + value*256) +end + +local telemetryPopTimeout = 0 +local function refreshNext() + if refreshState == 0 then + if calibrationState == 1 then + if telemetryWrite(0x9D, calibrationStep) == true then + refreshState = 1 + calibrationState = 2 + telemetryPopTimeout = getTime() + 80 -- normal delay is 500ms + end + elseif #modifications > 0 then + telemetryWrite(modifications[1][1], modifications[1][2]) + modifications[1] = nil + elseif refreshIndex < #fields then + local field = fields[refreshIndex + 1] + if telemetryRead(field[3]) == true then + refreshState = 1 + telemetryPopTimeout = getTime() + 80 -- normal delay is 500ms + end + end + elseif refreshState == 1 then + local physicalId, primId, dataId, value = sportTelemetryPop() + if physicalId == 0x1A and primId == 0x32 and dataId == 0x0C30 then + local fieldId = value % 256 + if calibrationState == 2 then + if fieldId == 0x9D then + refreshState = 0 + calibrationState = 0 + calibrationStep = (calibrationStep + 1) % 7 + end + else + local field = fields[refreshIndex + 1] + if fieldId == field[3] then + local value = math.floor(value / 256) + if field[3] >= 0x9E and field[3] <= 0xA0 then + local b1 = value % 256 + local b2 = math.floor(value / 256) + value = b1*256 + b2 + value = value - bit32.band(value, 0x8000) * 2 + end + if field[2] == COMBO and #field == 6 then + for index = 1, #(field[6]), 1 do + if value == field[6][index] then + value = index - 1 + break + end + end + elseif field[2] == VALUE and #field == 8 then + value = value - field[8] + field[5] + end + fields[refreshIndex + 1][4] = value + refreshIndex = refreshIndex + 1 + refreshState = 0 + end + end + elseif getTime() > telemetryPopTimeout then + refreshState = 0 + calibrationState = 0 + end + end +end + +local function updateField(field) + local value = field[4] + if field[2] == COMBO and #field == 6 then + value = field[6][1+value] + elseif field[2] == VALUE and #field == 8 then + value = value + field[8] - field[5] + end + modifications[#modifications+1] = { field[3], value } +end + +-- Main +local function runFieldsPage(event) + if event == EVT_EXIT_BREAK then -- exit script + return 2 + elseif event == EVT_ENTER_BREAK then -- toggle editing/selecting current field + if fields[current][4] ~= nil then + edit = not edit + if edit == false then + updateField(fields[current]) + end + end + elseif edit then + if event == EVT_PLUS_FIRST or event == EVT_ROT_RIGHT or event == EVT_PLUS_REPT then + addField(1) + elseif event == EVT_MINUS_FIRST or event == EVT_ROT_LEFT or event == EVT_MINUS_REPT then + addField(-1) + end + else + if event == EVT_MINUS_FIRST or event == EVT_ROT_LEFT then + selectField(1) + elseif event == EVT_PLUS_FIRST or event == EVT_ROT_RIGHT then + selectField(-1) + end + end + redrawFieldsPage() + return 0 +end + +local function drawCalibrationOrientation(x, y, step) + local orientation = { {"Label up.", "", 0, 0, 1000, 0, 0, 1000}, + {"Label down.", "", 0, 0, -1000, 0, 0, -1000}, + {"Pins Up.", "", -1000, 0, 0, 1000, 0, 0}, + {"Pins Down.", "", 1000, 0, 0, -1000, 0, 0}, + {"Label facing you", "Pins Right", 0, 1000, 0, 0, -1000, 0}, + {"Label facing you", "Pins Left", 0, -1000 , 0, 0, 1000, 0} } + + lcd.drawText(0, 9, "Place the SxR as follows:", 0) + lcd.drawText(x-9, y, orientation[step][1]) + lcd.drawText(x-9, y+10, orientation[step][2]) + local positionStatus = 0 + for index = 1, 3, 1 do + local field = fields[index] + lcd.drawText(90, 12+10*index, field[1], 0) + if math.abs(field[4] - orientation[step][2+index+orientationAutoSense]) < 200 then + lcd.drawNumber(100, 12+10*index, field[4]/10, LEFT+PREC2) + positionStatus = positionStatus + 1 + else + lcd.drawNumber(100, 12+10*index, field[4]/10, LEFT+PREC2+INVERS) + end + end + if step == 3 and positionStatus == 2 then -- orientation auto sensing + orientationAutoSense = 3 - orientationAutoSense + end + if positionStatus == 3 then + lcd.drawText(0, 56, " [Enter] to validate ", INVERS) + positionConfirmed = 1 + end +end + +local function runCalibrationPage(event) + fields = calibrationFields + if refreshIndex == #fields then + refreshIndex = 0 + end + lcd.clear() + lcd.drawScreenTitle("SxR Calibration", page, #pages) + if(calibrationStep < 6) then + drawCalibrationOrientation(10, 24, 1 + calibrationStep) + + local attr = calibrationState == 0 and INVERS or 0 + --lcd.drawText(0, 56, "[Enter] to validate", attr) + else + lcd.drawText(0, 19, "Calibration completed", 0) +-- lcd.drawText(10, 19, "Done",0) + lcd.drawText(0, 56, "Press [Exit] when ready", attr) + end + if calibrationStep > 6 and (event == EVT_ENTER_BREAK or event == EVT_EXIT_BREAK) then + return 2 + elseif event == EVT_ENTER_BREAK and positionConfirmed then + calibrationState = 1 + positionConfirmed = 0 + end + return 0 +end + + +-- Init +local function init() + current, edit, refreshState, refreshIndex = 1, false, 0, 0 + pages = { + runWarningPage, + runCalibrationPage + } +end + +-- Main +local function run(event) + if event == nil then + error("Cannot be run as a model script!") + return 2 + elseif event == EVT_PAGE_BREAK then + selectPage(1) + elseif event == EVT_PAGE_LONG then + killEvents(event); + selectPage(-1) + end + + local result = pages[page](event) + refreshNext() + + return result +end + +return { init=init, run=run } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x7/SxR/SxR.lua opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x7/SxR/SxR.lua --- opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x7/SxR/SxR.lua 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x7/SxR/SxR.lua 2017-11-11 11:29:14.000000000 +0000 @@ -0,0 +1,275 @@ +---- ######################################################################### +---- # # +---- # Copyright (C) OpenTX # +-----# # +---- # License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html # +---- # # +---- # This program is free software; you can redistribute it and/or modify # +---- # it under the terms of the GNU General Public License version 2 as # +---- # published by the Free Software Foundation. # +---- # # +---- # 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. # +---- # # +---- ######################################################################### +local VALUE = 0 +local COMBO = 1 + +local edit = false +local page = 1 +local current = 1 +local refreshState = 0 +local refreshIndex = 0 +local pageOffset = 0 +local pages = {} +local fields = {} +local modifications = {} + +local configFields = { + {"Wing type", COMBO, 0x80, nil, { "Normal", "Delta", "VTail" } }, + {"Mounting type", COMBO, 0x81, nil, { "Horz", "Horz rev.", "Vert", "Vert rev." } }, +} + +local settingsFields = { + {"SxR functions", COMBO, 0x9C, nil, { "Disable", "Enable" } }, + {"Quick Mode:", COMBO, 0xAA, nil, { "Disable", "Enable" } }, + {"CH5 mode", COMBO, 0xA8, nil, { "AIL2", "AUX1" } }, + {"CH6 mode", COMBO, 0xA9, nil, { "ELE2", "AUX2" } }, + {"AIL direction", COMBO, 0x82, nil, { "Normal", "Invers" }, { 255, 0 } }, + {"ELE direction", COMBO, 0x83, nil, { "Normal", "Invers" }, { 255, 0 } }, + {"RUD direction", COMBO, 0x84, nil, { "Normal", "Invers" }, { 255, 0 } }, + {"AIL2 direction", COMBO, 0x9A, nil, { "Normal", "Invers" }, { 255, 0 } }, + {"ELE2 direction", COMBO, 0x9B, nil, { "Normal", "Invers" }, { 255, 0 } }, + {"AIL stab gain", VALUE, 0x85, nil, 0, 200, "%"}, + {"ELE stab gain", VALUE, 0x86, nil, 0, 200, "%"}, + {"RUD stab gain", VALUE, 0x87, nil, 0, 200, "%"}, + {"AIL autolvl gain", VALUE, 0x88, nil, 0, 200, "%"}, + {"ELE autolvl gain", VALUE, 0x89, nil, 0, 200, "%"}, + {"ELE hover gain", VALUE, 0x8C, nil, 0, 200, "%"}, + {"RUD hover gain", VALUE, 0x8D, nil, 0, 200, "%"}, + {"AIL knife gain", VALUE, 0x8E, nil, 0, 200, "%"}, + {"RUD knife gain", VALUE, 0x90, nil, 0, 200, "%"}, + {"AIL autolvl offset", VALUE, 0x91, nil, -20, 20, "%", 0x6C}, + {"ELE autolvl offset", VALUE, 0x92, nil, -20, 20, "%", 0x6C}, + {"ELE hover offset", VALUE, 0x95, nil, -20, 20, "%", 0x6C}, + {"RUD hover offset", VALUE, 0x96, nil, -20, 20, "%", 0x6C}, + {"AIL knife offset", VALUE, 0x97, nil, -20, 20, "%", 0x6C}, + {"RUD knife offset", VALUE, 0x99, nil, -20, 20, "%", 0x6C}, +} + +-- Change display attribute to current field +local function addField(step) + local field = fields[current] + local min, max + if field[2] == VALUE then + min = field[5] + max = field[6] + elseif field[2] == COMBO then + min = 0 + max = #(field[5]) - 1 + end + if (step < 0 and field[4] > min) or (step > 0 and field[4] < max) then + field[4] = field[4] + step + end +end + +-- Select the next or previous page +local function selectPage(step) + page = 1 + ((page + step - 1 + #pages) % #pages) + refreshIndex = 0 + pageOffset = 0 +end + +-- Select the next or previous editable field +local function selectField(step) + current = 1 + ((current + step - 1 + #fields) % #fields) + if current > 7 + pageOffset then + pageOffset = current - 7 + elseif current <= pageOffset then + pageOffset = current - 1 + end +end + +local function drawProgressBar() + local width = (70 * refreshIndex) / #fields + lcd.drawRectangle(30, 1, 70, 6) + lcd.drawFilledRectangle(32, 3, width, 2); +end + +-- Redraw the current page +local function redrawFieldsPage() + lcd.clear() + lcd.drawScreenTitle("SxR", page, #pages) + + if refreshIndex < #fields then + drawProgressBar() + end + + for index = 1, 7, 1 do + local field = fields[pageOffset+index] + if field == nil then + break + end + + local attr = current == (pageOffset+index) and ((edit == true and BLINK or 0) + INVERS) or 0 + + lcd.drawText(0, 1+8*index, field[1]) + + if field[4] == nil then + lcd.drawText(LCD_W, 1+8*index, "---", attr + RIGHT) + else + if field[2] == VALUE then + lcd.drawNumber(LCD_W, 1+8*index, field[4], attr + RIGHT) + elseif field[2] == COMBO then + if field[4] >= 0 and field[4] < #(field[5]) then + lcd.drawText(LCD_W, 1+8*index, field[5][1+field[4]], attr + RIGHT) + end + end + end + end +end + +local function telemetryRead(field) + return sportTelemetryPush(0x17, 0x30, 0x0C30, field) +end + +local function telemetryWrite(field, value) + return sportTelemetryPush(0x17, 0x31, 0x0C30, field + value*256) +end + +local telemetryPopTimeout = 0 +local function refreshNext() + if refreshState == 0 then + if #modifications > 0 then + telemetryWrite(modifications[1][1], modifications[1][2]) + modifications[1] = nil + elseif refreshIndex < #fields then + local field = fields[refreshIndex + 1] + if telemetryRead(field[3]) == true then + refreshState = 1 + telemetryPopTimeout = getTime() + 120 -- normal delay is 500ms + end + end + elseif refreshState == 1 then + local physicalId, primId, dataId, value = sportTelemetryPop() + if physicalId == 0x1A and primId == 0x32 and dataId == 0x0C30 then + local fieldId = value % 256 + local field = fields[refreshIndex + 1] + if fieldId == field[3] then + local value = math.floor(value / 256) + if field[3] >= 0x9E and field[3] <= 0xA0 then + local b1 = value % 256 + local b2 = math.floor(value / 256) + value = b1*256 + b2 + value = value - bit32.band(value, 0x8000) * 2 + end + if field[2] == COMBO and #field == 6 then + for index = 1, #(field[6]), 1 do + if value == field[6][index] then + value = index - 1 + break + end + end + elseif field[2] == VALUE and #field == 8 then + value = value - field[8] + field[5] + end + fields[refreshIndex + 1][4] = value + refreshIndex = refreshIndex + 1 + refreshState = 0 + end + elseif getTime() > telemetryPopTimeout then + fields[refreshIndex + 1][4] = nil + refreshIndex = refreshIndex + 1 + refreshState = 0 + end + end +end + +local function updateField(field) + local value = field[4] + if field[2] == COMBO and #field == 6 then + value = field[6][1+value] + elseif field[2] == VALUE and #field == 8 then + value = value + field[8] - field[5] + end + modifications[#modifications+1] = { field[3], value } +end + +-- Main +local function runFieldsPage(event) + if event == EVT_EXIT_BREAK then -- exit script + return 2 + elseif event == EVT_ENTER_BREAK then -- toggle editing/selecting current field + if fields[current][4] ~= nil then + edit = not edit + if edit == false then + updateField(fields[current]) + end + end + elseif edit then + if event == EVT_PLUS_FIRST or event == EVT_ROT_RIGHT or event == EVT_PLUS_REPT then + addField(1) + elseif event == EVT_MINUS_FIRST or event == EVT_ROT_LEFT or event == EVT_MINUS_REPT then + addField(-1) + end + else + if event == EVT_MINUS_FIRST or event == EVT_ROT_RIGHT then + selectField(1) + elseif event == EVT_PLUS_FIRST or event == EVT_ROT_LEFT then + selectField(-1) + end + end + redrawFieldsPage() + return 0 +end + +local mountText = { "Label is facing the sky", "Label is facing ground", "Label is left when", "Label is right when" } + +local function runConfigPage(event) + fields = configFields + local result = runFieldsPage(event) + if fields[2][4] ~= nil then + lcd.drawText(1, 30, "Pins toward tail") + lcd.drawText(1, 40, mountText[1 + fields[2][4]]) + if fields[2][4] > 1 then + lcd.drawText(1, 50, "looking from the tail") + end + end + return result +end + +local function runSettingsPage(event) + fields = settingsFields + return runFieldsPage(event) +end + +-- Init +local function init() + current, edit, refreshState, refreshIndex = 1, false, 0, 0 + pages = { + runConfigPage, + runSettingsPage, + } +end + +-- Main +local function run(event) + if event == nil then + error("Cannot be run as a model script!") + return 2 + elseif event == EVT_PAGE_BREAK then + selectPage(1) + elseif event == EVT_PAGE_LONG then + killEvents(event); + selectPage(-1) + end + + local result = pages[page](event) + refreshNext() + + return result +end + +return { init=init, run=run } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/CROSSFIRE/crossfire.lua opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/CROSSFIRE/crossfire.lua --- opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/CROSSFIRE/crossfire.lua 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/CROSSFIRE/crossfire.lua 2017-10-31 16:16:43.000000000 +0000 @@ -1,3 +1,19 @@ +---- ######################################################################### +---- # # +---- # Copyright (C) OpenTX # +-----# # +---- # License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html # +---- # # +---- # This program is free software; you can redistribute it and/or modify # +---- # it under the terms of the GNU General Public License version 2 as # +---- # published by the Free Software Foundation. # +---- # # +---- # 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. # +---- # # +---- ######################################################################### local devices = { } local lineIndex = 1 local pageOffset = 0 diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/CROSSFIRE/device.lua opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/CROSSFIRE/device.lua --- opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/CROSSFIRE/device.lua 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/CROSSFIRE/device.lua 2017-10-31 16:16:43.000000000 +0000 @@ -1,3 +1,19 @@ +---- ######################################################################### +---- # # +---- # Copyright (C) OpenTX # +-----# # +---- # License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html # +---- # # +---- # This program is free software; you can redistribute it and/or modify # +---- # it under the terms of the GNU General Public License version 2 as # +---- # published by the Free Software Foundation. # +---- # # +---- # 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. # +---- # # +---- ######################################################################### local deviceId = 0 local deviceName = "" local lineIndex = 0 Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/S6R/bmp/back.bmp and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/S6R/bmp/back.bmp differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/S6R/bmp/delta.bmp and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/S6R/bmp/delta.bmp differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/S6R/bmp/done.bmp and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/S6R/bmp/done.bmp differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/S6R/bmp/down.bmp and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/S6R/bmp/down.bmp differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/S6R/bmp/forward.bmp and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/S6R/bmp/forward.bmp differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/S6R/bmp/horz.bmp and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/S6R/bmp/horz.bmp differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/S6R/bmp/horz-r.bmp and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/S6R/bmp/horz-r.bmp differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/S6R/bmp/left.bmp and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/S6R/bmp/left.bmp differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/S6R/bmp/plane.bmp and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/S6R/bmp/plane.bmp differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/S6R/bmp/right.bmp and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/S6R/bmp/right.bmp differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/S6R/bmp/up.bmp and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/S6R/bmp/up.bmp differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/S6R/bmp/vert.bmp and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/S6R/bmp/vert.bmp differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/S6R/bmp/vert-r.bmp and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/S6R/bmp/vert-r.bmp differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/S6R/bmp/vtail.bmp and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/S6R/bmp/vtail.bmp differ diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/S6R/S6R_Calibrate.lua opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/S6R/S6R_Calibrate.lua --- opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/S6R/S6R_Calibrate.lua 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/S6R/S6R_Calibrate.lua 1970-01-01 00:00:00.000000000 +0000 @@ -1,260 +0,0 @@ -local VALUE = 0 -local COMBO = 1 - -local COLUMN_2 = 150 - -local edit = false -local page = 1 -local current = 1 -local refreshState = 0 -local refreshIndex = 0 -local calibrationState = 0 -local pageOffset = 0 -local calibrationStep = 0 -local pages = {} -local fields = {} -local modifications = {} - -local calibrationFields = { - {"X:", VALUE, 0x9E, 0, -100, 100, "%"}, - {"Y:", VALUE, 0x9F, 0, -100, 100, "%"}, - {"Z:", VALUE, 0xA0, 0, -100, 100, "%"} -} - -local function drawProgressBar() - local width = (140 * refreshIndex) / #fields - lcd.drawRectangle(30, 1, 144, 6) - lcd.drawFilledRectangle(32, 3, width, 2); -end - --- Select the next or previous page -local function selectPage(step) - page = 1 + ((page + step - 1 + #pages) % #pages) - refreshIndex = 0 - calibrationStep = 0 - pageOffset = 0 -end - --- Draw initial warning page -local function runWarningPage(event) - lcd.clear() - lcd.drawScreenTitle("S6R", page, #pages) - lcd.drawText(0, 10, "Warning: this will start S6R calibration", SMLSIZE) - lcd.drawText(0, 20, "This need to be run only once. You need a S6R,", SMLSIZE) - lcd.drawText(0, 30, "power supply and a flat level surface (desk,...)", SMLSIZE) - lcd.drawText(0, 40, "Press [Enter] when ready", SMLSIZE) - lcd.drawText(0, 50, "Press [Exit] when cancel", SMLSIZE) - if event == EVT_ENTER_BREAK then - selectPage(1) - return 0 - elseif event == EVT_EXIT_BREAK then - return 2 - end - return 0 -end - --- Redraw the current page -local function redrawFieldsPage() - lcd.clear() - lcd.drawScreenTitle("S6R", page, #pages) - - if refreshIndex < #fields then - drawProgressBar() - end - - for index = 1, 7, 1 do - local field = fields[pageOffset+index] - if field == nil then - break - end - - local attr = current == (pageOffset+index) and ((edit == true and BLINK or 0) + INVERS) or 0 - - lcd.drawText(0, 1+8*index, field[1]) - - if field[4] == nil then - lcd.drawText(COLUMN_2, 1+8*index, "---", attr) - else - if field[2] == VALUE then - lcd.drawNumber(COLUMN_2, 1+8*index, field[4], LEFT + attr) - elseif field[2] == COMBO then - if field[4] >= 0 and field[4] < #(field[5]) then - lcd.drawText(COLUMN_2, 1+8*index, field[5][1+field[4]], attr) - end - end - end - end -end - -local function telemetryRead(field) - return sportTelemetryPush(0x17, 0x30, 0x0C30, field) -end - -local function telemetryWrite(field, value) - return sportTelemetryPush(0x17, 0x31, 0x0C30, field + value*256) -end - -local telemetryPopTimeout = 0 -local function refreshNext() - if refreshState == 0 then - if calibrationState == 1 then - if telemetryWrite(0x9D, calibrationStep) == true then - refreshState = 1 - calibrationState = 2 - telemetryPopTimeout = getTime() + 80 -- normal delay is 500ms - end - elseif #modifications > 0 then - telemetryWrite(modifications[1][1], modifications[1][2]) - modifications[1] = nil - elseif refreshIndex < #fields then - local field = fields[refreshIndex + 1] - if telemetryRead(field[3]) == true then - refreshState = 1 - telemetryPopTimeout = getTime() + 80 -- normal delay is 500ms - end - end - elseif refreshState == 1 then - local physicalId, primId, dataId, value = sportTelemetryPop() - if physicalId == 0x1A and primId == 0x32 and dataId == 0x0C30 then - local fieldId = value % 256 - if calibrationState == 2 then - if fieldId == 0x9D then - refreshState = 0 - calibrationState = 0 - calibrationStep = (calibrationStep + 1) % 7 - end - else - local field = fields[refreshIndex + 1] - if fieldId == field[3] then - local value = math.floor(value / 256) - if field[3] >= 0x9E and field[3] <= 0xA0 then - local b1 = value % 256 - local b2 = math.floor(value / 256) - value = b1*256 + b2 - value = value - bit32.band(value, 0x8000) * 2 - end - if field[2] == COMBO and #field == 6 then - for index = 1, #(field[6]), 1 do - if value == field[6][index] then - value = index - 1 - break - end - end - elseif field[2] == VALUE and #field == 8 then - value = value - field[8] + field[5] - end - fields[refreshIndex + 1][4] = value - refreshIndex = refreshIndex + 1 - refreshState = 0 - end - end - elseif getTime() > telemetryPopTimeout then - refreshState = 0 - calibrationState = 0 - end - end -end - -local function updateField(field) - local value = field[4] - if field[2] == COMBO and #field == 6 then - value = field[6][1+value] - elseif field[2] == VALUE and #field == 8 then - value = value + field[8] - field[5] - end - modifications[#modifications+1] = { field[3], value } -end - --- Main -local function runFieldsPage(event) - if event == EVT_EXIT_BREAK then -- exit script - return 2 - elseif event == EVT_ENTER_BREAK then -- toggle editing/selecting current field - if fields[current][4] ~= nil then - edit = not edit - if edit == false then - updateField(fields[current]) - end - end - elseif edit then - if event == EVT_PLUS_FIRST or event == EVT_ROT_RIGHT or event == EVT_PLUS_REPT then - addField(1) - elseif event == EVT_MINUS_FIRST or event == EVT_ROT_LEFT or event == EVT_MINUS_REPT then - addField(-1) - end - else - if event == EVT_MINUS_FIRST or event == EVT_ROT_LEFT then - selectField(1) - elseif event == EVT_PLUS_FIRST or event == EVT_ROT_RIGHT then - selectField(-1) - end - end - redrawFieldsPage() - return 0 -end - -local calibrationPositionsBitmaps = { "bmp/up.bmp", "bmp/down.bmp", "bmp/left.bmp", "bmp/right.bmp", "bmp/forward.bmp", "bmp/back.bmp" } - -local function runCalibrationPage(event) - fields = calibrationFields - if refreshIndex == #fields then - refreshIndex = 0 - end - lcd.clear() - lcd.drawScreenTitle("S6R", page, #pages) - if(calibrationStep < 6) then - lcd.drawText(0, 9, "Turn the S6R as shown", 0) - lcd.drawPixmap(10, 19, calibrationPositionsBitmaps[1 + calibrationStep]) - for index = 1, 3, 1 do - local field = fields[index] - lcd.drawText(80, 12+10*index, field[1], 0) - lcd.drawNumber(90, 12+10*index, field[4]/10, LEFT+PREC2) - end - - local attr = calibrationState == 0 and INVERS or 0 - lcd.drawText(0, 56, "Press [Enter] when ready", attr) - else - lcd.drawText(0, 9, "Calibration completed", 0) - lcd.drawPixmap(10, 19, "bmp/done.bmp") - lcd.drawText(0, 56, "Press [Exit] when ready", attr) - end - if calibrationStep > 6 and (event == EVT_ENTER_BREAK or event == EVT_EXIT_BREAK) then - return 2 - elseif event == EVT_ENTER_BREAK then - calibrationState = 1 - elseif event == EVT_EXIT_BREAK then - if calibrationStep > 0 then - calibrationStep = 0 - end - end - return 0 -end - --- Init -local function init() - current, edit, refreshState, refreshIndex = 1, false, 0, 0 - pages = { - runWarningPage, - runCalibrationPage - } -end - --- Main -local function run(event) - if event == nil then - error("Cannot be run as a model script!") - return 2 - elseif event == EVT_PAGE_BREAK then - selectPage(1) - elseif event == EVT_PAGE_LONG then - killEvents(event); - selectPage(-1) - end - - local result = pages[page](event) - refreshNext() - - return result -end - -return { init=init, run=run } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/S6R/S6R.lua opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/S6R/S6R.lua --- opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/S6R/S6R.lua 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/S6R/S6R.lua 1970-01-01 00:00:00.000000000 +0000 @@ -1,258 +0,0 @@ -local VALUE = 0 -local COMBO = 1 - -local COLUMN_2 = 150 - -local edit = false -local page = 1 -local current = 1 -local refreshState = 0 -local refreshIndex = 0 -local pageOffset = 0 -local pages = {} -local fields = {} -local modifications = {} - -local configFields = { - {"Wing type:", COMBO, 0x80, nil, { "Normal", "Delta", "VTail" } }, - {"Mounting type:", COMBO, 0x81, nil, { "Horz", "Horz rev.", "Vert", "Vert rev." } }, -} - -local settingsFields = { - {"S6R functions:", COMBO, 0x9C, nil, { "Disable", "Enable" } }, - {"CH5 mode:", COMBO, 0xA8, nil, { "AIL2", "AUX1" } }, - {"CH6 mode:", COMBO, 0xA9, nil, { "ELE2", "AUX2" } }, - {"AIL direction:", COMBO, 0x82, nil, { "Normal", "Invers" }, { 255, 0 } }, - {"ELE direction:", COMBO, 0x83, nil, { "Normal", "Invers" }, { 255, 0 } }, - {"RUD direction:", COMBO, 0x84, nil, { "Normal", "Invers" }, { 255, 0 } }, - {"AIL2 direction:", COMBO, 0x9A, nil, { "Normal", "Invers" }, { 255, 0 } }, - {"ELE2 direction:", COMBO, 0x9B, nil, { "Normal", "Invers" }, { 255, 0 } }, - {"AIL stabilize gain:", VALUE, 0x85, nil, 0, 200, "%"}, - {"ELE stabilize gain:", VALUE, 0x86, nil, 0, 200, "%"}, - {"RUD stabilize gain:", VALUE, 0x87, nil, 0, 200, "%"}, - {"AIL auto level gain:", VALUE, 0x88, nil, 0, 200, "%"}, - {"ELE auto level gain:", VALUE, 0x89, nil, 0, 200, "%"}, - {"ELE upright gain:", VALUE, 0x8C, nil, 0, 200, "%"}, - {"RUD upright gain:", VALUE, 0x8D, nil, 0, 200, "%"}, - {"AIL crab gain:", VALUE, 0x8E, nil, 0, 200, "%"}, - {"RUD crab gain:", VALUE, 0x90, nil, 0, 200, "%"}, - {"AIL auto angle offset:", VALUE, 0x91, nil, -20, 20, "%", 0x6C}, - {"ELE auto angle offset:", VALUE, 0x92, nil, -20, 20, "%", 0x6C}, - {"ELE upright angle offset:", VALUE, 0x95, nil, -20, 20, "%", 0x6C}, - {"RUD upright angle offset:", VALUE, 0x96, nil, -20, 20, "%", 0x6C}, - {"AIL crab angle offset:", VALUE, 0x97, nil, -20, 20, "%", 0x6C}, - {"RUD crab angle offset:", VALUE, 0x99, nil, -20, 20, "%", 0x6C}, -} - --- Change display attribute to current field -local function addField(step) - local field = fields[current] - local min, max - if field[2] == VALUE then - min = field[5] - max = field[6] - elseif field[2] == COMBO then - min = 0 - max = #(field[5]) - 1 - end - if (step < 0 and field[4] > min) or (step > 0 and field[4] < max) then - field[4] = field[4] + step - end -end - --- Select the next or previous page -local function selectPage(step) - page = 1 + ((page + step - 1 + #pages) % #pages) - refreshIndex = 0 - pageOffset = 0 -end - --- Select the next or previous editable field -local function selectField(step) - current = 1 + ((current + step - 1 + #fields) % #fields) - if current > 7 + pageOffset then - pageOffset = current - 7 - elseif current <= pageOffset then - pageOffset = current - 1 - end -end - -local function drawProgressBar() - local width = (140 * refreshIndex) / #fields - lcd.drawRectangle(30, 1, 144, 6) - lcd.drawFilledRectangle(32, 3, width, 2); -end - --- Redraw the current page -local function redrawFieldsPage() - lcd.clear() - lcd.drawScreenTitle("S6R", page, #pages) - - if refreshIndex < #fields then - drawProgressBar() - end - - for index = 1, 7, 1 do - local field = fields[pageOffset+index] - if field == nil then - break - end - - local attr = current == (pageOffset+index) and ((edit == true and BLINK or 0) + INVERS) or 0 - - lcd.drawText(0, 1+8*index, field[1]) - - if field[4] == nil then - lcd.drawText(COLUMN_2, 1+8*index, "---", attr) - else - if field[2] == VALUE then - lcd.drawNumber(COLUMN_2, 1+8*index, field[4], LEFT + attr) - elseif field[2] == COMBO then - if field[4] >= 0 and field[4] < #(field[5]) then - lcd.drawText(COLUMN_2, 1+8*index, field[5][1+field[4]], attr) - end - end - end - end -end - -local function telemetryRead(field) - return sportTelemetryPush(0x17, 0x30, 0x0C30, field) -end - -local function telemetryWrite(field, value) - return sportTelemetryPush(0x17, 0x31, 0x0C30, field + value*256) -end - -local telemetryPopTimeout = 0 -local function refreshNext() - if refreshState == 0 then - if #modifications > 0 then - telemetryWrite(modifications[1][1], modifications[1][2]) - modifications[1] = nil - elseif refreshIndex < #fields then - local field = fields[refreshIndex + 1] - if telemetryRead(field[3]) == true then - refreshState = 1 - telemetryPopTimeout = getTime() + 80 -- normal delay is 500ms - end - end - elseif refreshState == 1 then - local physicalId, primId, dataId, value = sportTelemetryPop() - if physicalId == 0x1A and primId == 0x32 and dataId == 0x0C30 then - local fieldId = value % 256 - local field = fields[refreshIndex + 1] - if fieldId == field[3] then - local value = math.floor(value / 256) - if field[3] >= 0x9E and field[3] <= 0xA0 then - local b1 = value % 256 - local b2 = math.floor(value / 256) - value = b1*256 + b2 - value = value - bit32.band(value, 0x8000) * 2 - end - if field[2] == COMBO and #field == 6 then - for index = 1, #(field[6]), 1 do - if value == field[6][index] then - value = index - 1 - break - end - end - elseif field[2] == VALUE and #field == 8 then - value = value - field[8] + field[5] - end - fields[refreshIndex + 1][4] = value - refreshIndex = refreshIndex + 1 - refreshState = 0 - end - elseif getTime() > telemetryPopTimeout then - refreshState = 0 - end - end -end - -local function updateField(field) - local value = field[4] - if field[2] == COMBO and #field == 6 then - value = field[6][1+value] - elseif field[2] == VALUE and #field == 8 then - value = value + field[8] - field[5] - end - modifications[#modifications+1] = { field[3], value } -end - --- Main -local function runFieldsPage(event) - if event == EVT_EXIT_BREAK then -- exit script - return 2 - elseif event == EVT_ENTER_BREAK then -- toggle editing/selecting current field - if fields[current][4] ~= nil then - edit = not edit - if edit == false then - updateField(fields[current]) - end - end - elseif edit then - if event == EVT_PLUS_FIRST or event == EVT_ROT_RIGHT or event == EVT_PLUS_REPT then - addField(1) - elseif event == EVT_MINUS_FIRST or event == EVT_ROT_LEFT or event == EVT_MINUS_REPT then - addField(-1) - end - else - if event == EVT_MINUS_FIRST or event == EVT_ROT_RIGHT then - selectField(1) - elseif event == EVT_PLUS_FIRST or event == EVT_ROT_LEFT then - selectField(-1) - end - end - redrawFieldsPage() - return 0 -end - -local wingBitmaps = { "bmp/plane.bmp", "bmp/delta.bmp", "bmp/vtail.bmp" } -local mountBitmaps = { "bmp/horz.bmp", "bmp/horz-r.bmp", "bmp/vert.bmp", "bmp/vert-r.bmp" } - -local function runConfigPage(event) - fields = configFields - local result = runFieldsPage(event) - if fields[1][4] ~= nil then - lcd.drawPixmap(20, 28, wingBitmaps[1 + fields[1][4]]) - end - if fields[2][4] ~= nil then - lcd.drawPixmap(128, 28, mountBitmaps[1 + fields[2][4]]) - end - return result -end - -local function runSettingsPage(event) - fields = settingsFields - return runFieldsPage(event) -end - --- Init -local function init() - current, edit, refreshState, refreshIndex = 1, false, 0, 0 - pages = { - runConfigPage, - runSettingsPage, - } -end - --- Main -local function run(event) - if event == nil then - error("Cannot be run as a model script!") - return 2 - elseif event == EVT_PAGE_BREAK then - selectPage(1) - elseif event == EVT_PAGE_LONG then - killEvents(event); - selectPage(-1) - end - - local result = pages[page](event) - refreshNext() - - return result -end - -return { init=init, run=run } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/SCRIPTS/TEMPLATES/readme.txt opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/SCRIPTS/TEMPLATES/readme.txt --- opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/SCRIPTS/TEMPLATES/readme.txt 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/SCRIPTS/TEMPLATES/readme.txt 1970-01-01 00:00:00.000000000 +0000 @@ -1 +0,0 @@ -This directory is for template lua scripts. diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/SCRIPTS/WIZARD/delta.lua opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/SCRIPTS/WIZARD/delta.lua --- opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/SCRIPTS/WIZARD/delta.lua 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/SCRIPTS/WIZARD/delta.lua 2017-12-17 16:22:27.000000000 +0000 @@ -1,3 +1,19 @@ +---- ######################################################################### +---- # # +---- # Copyright (C) OpenTX # +-----# # +---- # License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html # +---- # # +---- # This program is free software; you can redistribute it and/or modify # +---- # it under the terms of the GNU General Public License version 2 as # +---- # published by the Free Software Foundation. # +---- # # +---- # 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. # +---- # # +---- ######################################################################### -- Delta Wizard pages local ENGINE_PAGE = 0 local ELEVONS_PAGE = 1 @@ -122,7 +138,7 @@ end -- Engine Menu -local engineModeItems = {"No", "Yes..."} +local engineModeItems = {"No", "Yes"} local function drawEngineMenu() lcd.clear() lcd.drawText(1, 0, "Has your model got an engine?", 0) @@ -190,7 +206,7 @@ end -- Rudder menu -local rudderModeItems = {"No", "Yes..."} +local rudderModeItems = {"No", "Yes"} local function drawRudderMenu() lcd.clear() @@ -292,10 +308,10 @@ if engineMode == 1 then addMix(thrCH1, MIXSRC_FIRST_INPUT+defaultChannel(2), "Engine") end - addMix(elevCH1, MIXSRC_FIRST_INPUT+defaultChannel(1), "Elev1-E", 50) - addMix(elevCH1, MIXSRC_FIRST_INPUT+defaultChannel(3), "Elev1-A", 50, 1) - addMix(elevCH2, MIXSRC_FIRST_INPUT+defaultChannel(1), "Elev2-E", 50) - addMix(elevCH2, MIXSRC_FIRST_INPUT+defaultChannel(3), "Elev2-A", -50, 1) + addMix(elevCH1, MIXSRC_FIRST_INPUT+defaultChannel(1), "D-EleL", 50) + addMix(elevCH1, MIXSRC_FIRST_INPUT+defaultChannel(3), "D-AilL", 50, 1) + addMix(elevCH2, MIXSRC_FIRST_INPUT+defaultChannel(1), "D-EleR", 50) + addMix(elevCH2, MIXSRC_FIRST_INPUT+defaultChannel(3), "D-AilR", -50, 1) if rudderMode == 1 then addMix(rudCH1, MIXSRC_FIRST_INPUT+defaultChannel(0), "Rudder") end @@ -303,6 +319,7 @@ local function drawNextLine(x, y, label, channel) lcd.drawText(x, y, label, 0); + lcd.drawText(x+48, y, ":", 0); lcd.drawSource(x+52, y, MIXSRC_CH1+channel, 0) y = y + 8 if y > 50 then @@ -319,17 +336,16 @@ lcd.drawText(48, 1, "Ready to go?", 0); lcd.drawFilledRectangle(0, 0, LCD_W, 9, 0) if engineMode == 1 then - x, y = drawNextLine(x, y, "Throttle:", thrCH1) + x, y = drawNextLine(x, y, "Throttle", thrCH1) end - x, y = drawNextLine(x, y, "Elevons:", elevCH1) - x, y = drawNextLine(x, y, "Elevons:", elevCH2) + x, y = drawNextLine(x, y, "Elev L", elevCH1) + x, y = drawNextLine(x, y, "Elev R", elevCH2) if rudderMode == 1 then drawNextLine(x, y, "Rudder:", rudCH1) end - lcd.drawText(48, LCD_H-8, "[Enter Long] to confirm", 0); + lcd.drawText(48, LCD_H-8, "Long [ENT] to confirm", 0); lcd.drawFilledRectangle(0, LCD_H-9, LCD_W, 9, 0) - lcd.drawPixmap(LCD_W-18, 0, "confirm-tick.bmp") - lcd.drawPixmap(0, LCD_H-17, "confirm-plane.bmp") + lcd.drawPixmap(LCD_W-18, LCD_H-17, "confirm-tick.bmp") fieldsMax = 0 end diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/SCRIPTS/WIZARD/multi.lua opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/SCRIPTS/WIZARD/multi.lua --- opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/SCRIPTS/WIZARD/multi.lua 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/SCRIPTS/WIZARD/multi.lua 2017-12-17 16:22:27.000000000 +0000 @@ -1,3 +1,19 @@ +---- ######################################################################### +---- # # +---- # Copyright (C) OpenTX # +-----# # +---- # License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html # +---- # # +---- # This program is free software; you can redistribute it and/or modify # +---- # it under the terms of the GNU General Public License version 2 as # +---- # published by the Free Software Foundation. # +---- # # +---- # 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. # +---- # # +---- ######################################################################### -- Multicopter Wizard pages local THROTTLE_PAGE = 0 local ROLL_PAGE = 1 @@ -11,7 +27,6 @@ local edit = false local field = 0 local fieldsMax = 0 -local comboBoxMode = 0 -- Scrap variable -- Model settings local thrCH1 = 0 @@ -124,11 +139,9 @@ lcd.clear() lcd.drawText(1, 0, "Select multicopter throttle channel", 0) lcd.drawFilledRectangle(0, 0, LCD_W, 8, GREY_DEFAULT+FILL_WHITE) - lcd.drawCombobox(0, 8, LCD_W/2, {"..."}, comboBoxMode, getFieldFlags(1)) lcd.drawLine(LCD_W/2-1, 18, LCD_W/2-1, LCD_H-1, DOTTED, 0) lcd.drawPixmap(120, 8, "multi-thr.bmp") - lcd.drawText(20, LCD_H-16, "Assign Throttle", 0); - lcd.drawText(20, LCD_H-8, "Channel", 0); + lcd.drawText(25, LCD_H-16, "Assign channel", 0); lcd.drawText(LCD_W/2-19, LCD_H-8, ">>>", 0); lcd.drawSource(113, LCD_H-8, MIXSRC_CH1+thrCH1, getFieldFlags(0)) fieldsMax = 0 @@ -148,11 +161,9 @@ lcd.clear() lcd.drawText(1, 0, "Select multicopter roll channel", 0) lcd.drawFilledRectangle(0, 0, LCD_W, 8, GREY_DEFAULT+FILL_WHITE) - lcd.drawCombobox(0, 8, LCD_W/2, {"..."}, comboBoxMode, getFieldFlags(1)) lcd.drawLine(LCD_W/2-1, 18, LCD_W/2-1, LCD_H-1, DOTTED, 0) lcd.drawPixmap(120, 8, "multi-roll.bmp") - lcd.drawText(20, LCD_H-16, "Assign Roll", 0); - lcd.drawText(20, LCD_H-8, "Channel", 0); + lcd.drawText(25, LCD_H-16, "Assign channel", 0); lcd.drawText(LCD_W/2-19, LCD_H-8, ">>>", 0); lcd.drawSource(113, LCD_H-8, MIXSRC_CH1+rollCH1, getFieldFlags(0)) fieldsMax = 0 @@ -172,11 +183,9 @@ lcd.clear() lcd.drawText(1, 0, "Select multicopter pitch channel", 0) lcd.drawFilledRectangle(0, 0, LCD_W, 8, GREY_DEFAULT+FILL_WHITE) - lcd.drawCombobox(0, 8, LCD_W/2, {"..."}, comboBoxMode, getFieldFlags(1)) lcd.drawLine(LCD_W/2-1, 18, LCD_W/2-1, LCD_H-1, DOTTED, 0) lcd.drawPixmap(120, 8, "multi-pitch.bmp") - lcd.drawText(20, LCD_H-16, "Assign Pitch", 0); - lcd.drawText(20, LCD_H-8, "Channel", 0); + lcd.drawText(25, LCD_H-16, "Assign channel", 0); lcd.drawText(LCD_W/2-19, LCD_H-8, ">>>", 0); lcd.drawSource(113, LCD_H-8, MIXSRC_CH1+pitchCH1, getFieldFlags(0)) fieldsMax = 0 @@ -196,11 +205,9 @@ lcd.clear() lcd.drawText(1, 0, "Select multicopter yaw channel", 0) lcd.drawFilledRectangle(0, 0, LCD_W, 8, GREY_DEFAULT+FILL_WHITE) - lcd.drawCombobox(0, 8, LCD_W/2, {"..."}, comboBoxMode, getFieldFlags(1)) lcd.drawLine(LCD_W/2-1, 18, LCD_W/2-1, LCD_H-1, DOTTED, 0) lcd.drawPixmap(120, 8, "multi-yaw.bmp") - lcd.drawText(20, LCD_H-16, "Assign Yaw", 0); - lcd.drawText(20, LCD_H-8, "Channel", 0); + lcd.drawText(25, LCD_H-16, "Assign channel", 0); lcd.drawText(LCD_W/2-19, LCD_H-8, ">>>", 0); lcd.drawSource(113, LCD_H-8, MIXSRC_CH1+yawCH1, getFieldFlags(0)) fieldsMax = 0 @@ -218,6 +225,7 @@ -- Confirmation Menu local function drawNextLine(x, y, label, channel) lcd.drawText(x, y, label, 0); + lcd.drawText(x+48, y, ":", 0); lcd.drawSource(x+52, y, MIXSRC_CH1+channel, 0) y = y + 8 if y > 50 then @@ -233,14 +241,13 @@ lcd.clear() lcd.drawText(48, 1, "Ready to go?", 0); lcd.drawFilledRectangle(0, 0, LCD_W, 9, 0) - x, y = drawNextLine(x, y, "Throttle:", thrCH1) - x, y = drawNextLine(x, y, "Roll:", rollCH1) - x, y = drawNextLine(x, y, "Pitch:", pitchCH1) - x, y = drawNextLine(x, y, "Yaw:", yawCH1) - lcd.drawText(48, LCD_H-8, "[Enter Long] to confirm", 0); + x, y = drawNextLine(x, y, "Throttle", thrCH1) + x, y = drawNextLine(x, y, "Roll", rollCH1) + x, y = drawNextLine(x, y, "Pitch", pitchCH1) + x, y = drawNextLine(x, y, "Yaw", yawCH1) + lcd.drawText(48, LCD_H-8, "Long [ENT] to confirm", 0); lcd.drawFilledRectangle(0, LCD_H-9, LCD_W, 9, 0) - lcd.drawPixmap(LCD_W-18, 0, "confirm-tick.bmp") - lcd.drawPixmap(0, LCD_H-17, "confirm-plane.bmp") + lcd.drawPixmap(LCD_W-18, LCD_H-17, "confirm-tick.bmp") fieldsMax = 0 end @@ -258,7 +265,7 @@ local function applySettings() model.defaultInputs() model.deleteMixes() - addMix(thrCH1, MIXSRC_FIRST_INPUT+defaultChannel(2), "Throttle") + addMix(thrCH1, MIXSRC_FIRST_INPUT+defaultChannel(2), "Engine") addMix(rollCH1, MIXSRC_FIRST_INPUT+defaultChannel(3), "Roll") addMix(yawCH1, MIXSRC_FIRST_INPUT+defaultChannel(0), "Yaw") addMix(pitchCH1, MIXSRC_FIRST_INPUT+defaultChannel(1), "Pitch") diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/SCRIPTS/WIZARD/plane.lua opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/SCRIPTS/WIZARD/plane.lua --- opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/SCRIPTS/WIZARD/plane.lua 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/SCRIPTS/WIZARD/plane.lua 2017-12-17 16:22:27.000000000 +0000 @@ -1,3 +1,19 @@ +---- ######################################################################### +---- # # +---- # Copyright (C) OpenTX # +-----# # +---- # License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html # +---- # # +---- # This program is free software; you can redistribute it and/or modify # +---- # it under the terms of the GNU General Public License version 2 as # +---- # published by the Free Software Foundation. # +---- # # +---- # 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. # +---- # # +---- ######################################################################### -- Plane Wizard pages local ENGINE_PAGE = 0 local AILERONS_PAGE = 1 @@ -18,16 +34,16 @@ local thrCH1 = 0 local aileronsMode = 1 local ailCH1 = 0 -local ailCH2 = 4 +local ailCH2 = 5 local flapsMode = 0 -local flapsCH1 = 5 -local flapsCH2 = 6 +local flapsCH1 = 6 +local flapsCH2 = 7 local brakesMode = 0 local brakesCH1 = 8 local brakesCH2 = 9 local tailMode = 1 local eleCH1 = 0 -local eleCH2 = 7 +local eleCH2 = 4 local rudCH1 = 0 local servoPage = nil @@ -132,7 +148,7 @@ end -- Engine Menu -local engineModeItems = {"No", "Yes..."} +local engineModeItems = {"No", "Yes"} local function drawEngineMenu() lcd.clear() lcd.drawText(1, 0, "Has your model got an engine?", 0) @@ -169,7 +185,7 @@ end -- Ailerons Menu -local aileronsModeItems = {"No", "Yes...", "Yes, 2 channels..."} +local aileronsModeItems = {"No", "Yes, 1 channel", "Yes, 2 channels"} local function drawAileronsMenu() lcd.clear() lcd.drawText(1, 0, "Has your model got ailerons?", 0) @@ -216,7 +232,7 @@ end -- Flaps Menu -local flapsModeItems = {"No", "Yes...", "Yes, 2 channels..."} +local flapsModeItems = {"No", "Yes, 1 channel", "Yes, 2 channels"} local function drawFlapsMenu() lcd.clear() lcd.drawText(1, 0, "Has your model got flaps?", 0) @@ -263,7 +279,7 @@ end -- Airbrakes Menu -local brakesModeItems = {"No", "Yes...", "Yes, 2 channels..."} +local brakesModeItems = {"No", "Yes, 1 channel", "Yes, 2 channels"} local function drawBrakesMenu() lcd.clear() lcd.drawText(1, 0, "Has your model got air brakes?", 0) @@ -310,7 +326,7 @@ end -- Tail Menu -local tailModeItems = {"Ele(1ch), no Rud...", "Ele(1ch) + Rud...", "Ele(2ch) + Rud...", "V-Tail..."} +local tailModeItems = {"Ele(1ch)", "Ele(1ch) + Rud(1ch)", "Ele(2ch) + Rud(1ch)", "V-Tail(2ch)"} local function drawTailMenu() lcd.clear() lcd.drawText(1, 0, "Which is the tail config on your model?", 0) @@ -418,6 +434,7 @@ -- Confirmation Menu local function drawNextLine(x, y, label, channel) lcd.drawText(x, y, label, 0); + lcd.drawText(x+48, y, ":", 0); lcd.drawSource(x+52, y, MIXSRC_CH1+channel, 0) y = y + 8 if y > 50 then @@ -434,40 +451,41 @@ lcd.drawText(48, 1, "Ready to go?", 0); lcd.drawFilledRectangle(0, 0, LCD_W, 9, 0) if engineMode == 1 then - x, y = drawNextLine(x, y, "Throttle:", thrCH1) + x, y = drawNextLine(x, y, "Throttle", thrCH1) end - if aileronsMode > 0 then - x, y = drawNextLine(x, y, "Ailerons:", ailCH1) - if aileronsMode == 2 then - x, y = drawNextLine(x, y, "Ailerons:", ailCH2) - end + if aileronsMode == 1 then + x, y = drawNextLine(x, y, "Ail", ailCH1) + elseif aileronsMode == 2 then + x, y = drawNextLine(x, y, "Ail L", ailCH1) + x, y = drawNextLine(x, y, "Ail R", ailCH2) end - if flapsMode > 0 then - x, y = drawNextLine(x, y, "Flaps:", flapsCH1) - if flapsMode == 2 then - x, y = drawNextLine(x, y, "Flaps:", flapsCH2) - end + if flapsMode == 1 then + x, y = drawNextLine(x, y, "Flaps", flapsCH1) + elseif flapsMode == 2 then + x, y = drawNextLine(x, y, "Flap L", flapsCH1) + x, y = drawNextLine(x, y, "Flap R", flapsCH2) end - if brakesMode > 0 then - x, y = drawNextLine(x, y, "Brakes:", brakesCH1) - if brakesMode == 2 then - x, y = drawNextLine(x, y, "Brakes:", brakesCH2) - end + if brakesMode == 1 then + x, y = drawNextLine(x, y, "Brakes", brakesCH1) + elseif brakesMode == 2 then + x, y = drawNextLine(x, y, "Brake L", brakesCH1) + x, y = drawNextLine(x, y, "Brake R", brakesCH2) end if tailMode == 3 then - x, y = drawNextLine(x, y, "V-Tail:", eleCH1) - x, y = drawNextLine(x, y, "V-Tail:", eleCH2) + x, y = drawNextLine(x, y, "V-Tail L", eleCH1) + x, y = drawNextLine(x, y, "V-Tail R", eleCH2) else - x, y = drawNextLine(x, y, "Elevator:", eleCH1) - if tailMode == 2 then - x, y = drawNextLine(x, y, "Elevator:", eleCH2) + x, y = drawNextLine(x, y, "Rudder", rudCH1) + if tailMode == 1 then + x, y = drawNextLine(x, y, "Elev", eleCH1) + elseif tailMode == 2 then + x, y = drawNextLine(x, y, "Elev L", eleCH1) + x, y = drawNextLine(x, y, "Elev R", eleCH2) end - drawNextLine(x, y, "Rudder:", rudCH1) end - lcd.drawText(48, LCD_H-8, "[Enter Long] to confirm", 0); + lcd.drawText(48, LCD_H-8, "Long [ENT] to confirm", 0); lcd.drawFilledRectangle(0, LCD_H-9, LCD_W, 9, 0) - lcd.drawPixmap(LCD_W-18, 0, "confirm-tick.bmp") - lcd.drawPixmap(0, LCD_H-17, "confirm-plane.bmp") + lcd.drawPixmap(LCD_W-18, LCD_H-17, "confirm-tick.bmp") fieldsMax = 0 end @@ -488,36 +506,38 @@ if engineMode > 0 then addMix(thrCH1, MIXSRC_FIRST_INPUT+defaultChannel(2), "Engine") end - if aileronsMode > 0 then - addMix(ailCH1, MIXSRC_FIRST_INPUT+defaultChannel(3), "Aileron") - if aileronsMode == 2 then - addMix(ailCH2, MIXSRC_FIRST_INPUT+defaultChannel(3), "Aileron", -100) - end + if aileronsMode == 1 then + addMix(ailCH1, MIXSRC_FIRST_INPUT+defaultChannel(3), "Ail") + elseif aileronsMode == 2 then + addMix(ailCH1, MIXSRC_FIRST_INPUT+defaultChannel(3), "AilL") + addMix(ailCH2, MIXSRC_FIRST_INPUT+defaultChannel(3), "AilR", -100) end - if flapsMode > 0 then - addMix(flapsCH1, MIXSRC_SA, "Flap") - if flapsMode == 2 then - addMix(flapsCH2, MIXSRC_SA, "Flap") - end + if flapsMode == 1 then + addMix(flapsCH1, MIXSRC_SA, "Flaps") + elseif flapsMode == 2 then + addMix(flapsCH1, MIXSRC_SA, "FlapL") + addMix(flapsCH2, MIXSRC_SA, "FlapR") end - if brakesMode > 0 then - addMix(brakesCH1, MIXSRC_SE, "Brake") - if brakesMode == 2 then - addMix(brakesCH2, MIXSRC_SE, "Brake") - end + if brakesMode == 1 then + addMix(brakesCH1, MIXSRC_SE, "Brakes") + elseif brakesMode == 2 then + addMix(brakesCH1, MIXSRC_SE, "BrakeL") + addMix(brakesCH2, MIXSRC_SE, "BrakeR") end if tailMode == 3 then - addMix(eleCH1, MIXSRC_FIRST_INPUT+defaultChannel(1), "V-Tail-E", 50) - addMix(eleCH1, MIXSRC_FIRST_INPUT+defaultChannel(0), "V-Tail-R", 50, 1) - addMix(eleCH2, MIXSRC_FIRST_INPUT+defaultChannel(1), "V-Tail-E", 50) - addMix(eleCH2, MIXSRC_FIRST_INPUT+defaultChannel(0), "V-Tail-R", -50, 1) + addMix(eleCH1, MIXSRC_FIRST_INPUT+defaultChannel(1), "V-EleL", 50) + addMix(eleCH1, MIXSRC_FIRST_INPUT+defaultChannel(0), "V-RudL", 50, 1) + addMix(eleCH2, MIXSRC_FIRST_INPUT+defaultChannel(1), "V-EleR", 50) + addMix(eleCH2, MIXSRC_FIRST_INPUT+defaultChannel(0), "V-RudR", -50, 1) else - addMix(eleCH1, MIXSRC_FIRST_INPUT+defaultChannel(1), "Elevator") if tailMode > 0 then addMix(rudCH1, MIXSRC_FIRST_INPUT+defaultChannel(0), "Rudder") end - if tailMode == 2 then - addMix(eleCH2, MIXSRC_FIRST_INPUT+defaultChannel(1), "Elevator") + if tailMode == 1 then + addMix(eleCH1, MIXSRC_FIRST_INPUT+defaultChannel(1), "Elev") + elseif tailMode == 2 then + addMix(eleCH1, MIXSRC_FIRST_INPUT+defaultChannel(1), "ElevL") + addMix(eleCH2, MIXSRC_FIRST_INPUT+defaultChannel(1), "ElevR") end end end diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/SCRIPTS/WIZARD/wizard.lua opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/SCRIPTS/WIZARD/wizard.lua --- opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/SCRIPTS/WIZARD/wizard.lua 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/SCRIPTS/WIZARD/wizard.lua 2017-11-11 11:29:14.000000000 +0000 @@ -1,10 +1,25 @@ +---- ######################################################################### +---- # # +---- # Copyright (C) OpenTX # +-----# # +---- # License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html # +---- # # +---- # This program is free software; you can redistribute it and/or modify # +---- # it under the terms of the GNU General Public License version 2 as # +---- # published by the Free Software Foundation. # +---- # # +---- # 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. # +---- # # +---- ######################################################################### -- Navigation variables local dirty = true -- Model types local modelType = 0 local MODELTYPE_PLANE = 0 ---local MODELTYPE_HELI = 1 local MODELTYPE_DELTA = 1 local MODELTYPE_QUAD = 2 @@ -23,18 +38,16 @@ -- Model Type Menu local function modelTypeSurround(index) - lcd.drawRectangle(12+47*index, 13, 48, 48) - lcd.drawPixmap(17+47*index, 8, "mark.bmp") + lcd.drawRectangle(17+65*index, 14, 48, 48) + lcd.drawPixmap(22+65*index, 9, "mark.bmp") end local function drawModelChoiceMenu() lcd.clear() - lcd.drawScreenTitle("", 0, 0) - -- lcd.drawText(58, 13, "Select model type", 0) - lcd.drawPixmap( 16, 17, "plane.bmp") - --lcd.drawPixmap( 63, 17, "heli.bmp") - lcd.drawPixmap(63, 17, "delta.bmp") - lcd.drawPixmap(110, 17, "quadri.bmp") + lcd.drawScreenTitle("Select model type", 0, 0) + lcd.drawPixmap(21, 18, "plane.bmp") + lcd.drawPixmap(86, 18, "delta.bmp") + lcd.drawPixmap(151, 18, "quadri.bmp") modelTypeSurround(modelType) end @@ -46,7 +59,6 @@ if event == EVT_ENTER_BREAK then if modelType == MODELTYPE_PLANE then return "plane.lua" - elseif modelType == MODELTYPE_HELI then elseif modelType == MODELTYPE_DELTA then return "delta.lua" elseif modelType == MODELTYPE_QUAD then Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/SxR/bmp/back.bmp and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/SxR/bmp/back.bmp differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/SxR/bmp/delta.bmp and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/SxR/bmp/delta.bmp differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/SxR/bmp/done.bmp and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/SxR/bmp/done.bmp differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/SxR/bmp/down.bmp and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/SxR/bmp/down.bmp differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/SxR/bmp/forward.bmp and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/SxR/bmp/forward.bmp differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/SxR/bmp/horz.bmp and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/SxR/bmp/horz.bmp differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/SxR/bmp/horz-r.bmp and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/SxR/bmp/horz-r.bmp differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/SxR/bmp/left.bmp and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/SxR/bmp/left.bmp differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/SxR/bmp/plane.bmp and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/SxR/bmp/plane.bmp differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/SxR/bmp/right.bmp and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/SxR/bmp/right.bmp differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/SxR/bmp/up.bmp and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/SxR/bmp/up.bmp differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/SxR/bmp/vert.bmp and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/SxR/bmp/vert.bmp differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/SxR/bmp/vert-r.bmp and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/SxR/bmp/vert-r.bmp differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/SxR/bmp/vtail.bmp and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/SxR/bmp/vtail.bmp differ diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/SxR/SxR_Calibrate.lua opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/SxR/SxR_Calibrate.lua --- opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/SxR/SxR_Calibrate.lua 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/SxR/SxR_Calibrate.lua 2017-11-11 11:29:14.000000000 +0000 @@ -0,0 +1,276 @@ +---- ######################################################################### +---- # # +---- # Copyright (C) OpenTX # +-----# # +---- # License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html # +---- # # +---- # This program is free software; you can redistribute it and/or modify # +---- # it under the terms of the GNU General Public License version 2 as # +---- # published by the Free Software Foundation. # +---- # # +---- # 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. # +---- # # +---- ######################################################################### +local VALUE = 0 +local COMBO = 1 + +local COLUMN_2 = 150 + +local edit = false +local page = 1 +local current = 1 +local refreshState = 0 +local refreshIndex = 0 +local calibrationState = 0 +local pageOffset = 0 +local calibrationStep = 0 +local pages = {} +local fields = {} +local modifications = {} + +local calibrationFields = { + {"X:", VALUE, 0x9E, 0, -100, 100, "%"}, + {"Y:", VALUE, 0x9F, 0, -100, 100, "%"}, + {"Z:", VALUE, 0xA0, 0, -100, 100, "%"} +} + +local function drawProgressBar() + local width = (140 * refreshIndex) / #fields + lcd.drawRectangle(30, 1, 144, 6) + lcd.drawFilledRectangle(32, 3, width, 2); +end + +-- Select the next or previous page +local function selectPage(step) + page = 1 + ((page + step - 1 + #pages) % #pages) + refreshIndex = 0 + calibrationStep = 0 + pageOffset = 0 +end + +-- Draw initial warning page +local function runWarningPage(event) + lcd.clear() + lcd.drawScreenTitle("SxR", page, #pages) + lcd.drawText(0, 10, "Warning: this will start SxR calibration", SMLSIZE) + lcd.drawText(0, 20, "This need to be run only once. You need a SxR,", SMLSIZE) + lcd.drawText(0, 30, "power supply and a flat level surface (desk,...)", SMLSIZE) + lcd.drawText(0, 40, "Press [Enter] when ready", SMLSIZE) + lcd.drawText(0, 50, "Press [Exit] when cancel", SMLSIZE) + if event == EVT_ENTER_BREAK then + selectPage(1) + return 0 + elseif event == EVT_EXIT_BREAK then + return 2 + end + return 0 +end + +-- Redraw the current page +local function redrawFieldsPage() + lcd.clear() + lcd.drawScreenTitle("SxR", page, #pages) + + if refreshIndex < #fields then + drawProgressBar() + end + + for index = 1, 7, 1 do + local field = fields[pageOffset+index] + if field == nil then + break + end + + local attr = current == (pageOffset+index) and ((edit == true and BLINK or 0) + INVERS) or 0 + + lcd.drawText(0, 1+8*index, field[1]) + + if field[4] == nil then + lcd.drawText(COLUMN_2, 1+8*index, "---", attr) + else + if field[2] == VALUE then + lcd.drawNumber(COLUMN_2, 1+8*index, field[4], LEFT + attr) + elseif field[2] == COMBO then + if field[4] >= 0 and field[4] < #(field[5]) then + lcd.drawText(COLUMN_2, 1+8*index, field[5][1+field[4]], attr) + end + end + end + end +end + +local function telemetryRead(field) + return sportTelemetryPush(0x17, 0x30, 0x0C30, field) +end + +local function telemetryWrite(field, value) + return sportTelemetryPush(0x17, 0x31, 0x0C30, field + value*256) +end + +local telemetryPopTimeout = 0 +local function refreshNext() + if refreshState == 0 then + if calibrationState == 1 then + if telemetryWrite(0x9D, calibrationStep) == true then + refreshState = 1 + calibrationState = 2 + telemetryPopTimeout = getTime() + 80 -- normal delay is 500ms + end + elseif #modifications > 0 then + telemetryWrite(modifications[1][1], modifications[1][2]) + modifications[1] = nil + elseif refreshIndex < #fields then + local field = fields[refreshIndex + 1] + if telemetryRead(field[3]) == true then + refreshState = 1 + telemetryPopTimeout = getTime() + 80 -- normal delay is 500ms + end + end + elseif refreshState == 1 then + local physicalId, primId, dataId, value = sportTelemetryPop() + if physicalId == 0x1A and primId == 0x32 and dataId == 0x0C30 then + local fieldId = value % 256 + if calibrationState == 2 then + if fieldId == 0x9D then + refreshState = 0 + calibrationState = 0 + calibrationStep = (calibrationStep + 1) % 7 + end + else + local field = fields[refreshIndex + 1] + if fieldId == field[3] then + local value = math.floor(value / 256) + if field[3] >= 0x9E and field[3] <= 0xA0 then + local b1 = value % 256 + local b2 = math.floor(value / 256) + value = b1*256 + b2 + value = value - bit32.band(value, 0x8000) * 2 + end + if field[2] == COMBO and #field == 6 then + for index = 1, #(field[6]), 1 do + if value == field[6][index] then + value = index - 1 + break + end + end + elseif field[2] == VALUE and #field == 8 then + value = value - field[8] + field[5] + end + fields[refreshIndex + 1][4] = value + refreshIndex = refreshIndex + 1 + refreshState = 0 + end + end + elseif getTime() > telemetryPopTimeout then + refreshState = 0 + calibrationState = 0 + end + end +end + +local function updateField(field) + local value = field[4] + if field[2] == COMBO and #field == 6 then + value = field[6][1+value] + elseif field[2] == VALUE and #field == 8 then + value = value + field[8] - field[5] + end + modifications[#modifications+1] = { field[3], value } +end + +-- Main +local function runFieldsPage(event) + if event == EVT_EXIT_BREAK then -- exit script + return 2 + elseif event == EVT_ENTER_BREAK then -- toggle editing/selecting current field + if fields[current][4] ~= nil then + edit = not edit + if edit == false then + updateField(fields[current]) + end + end + elseif edit then + if event == EVT_PLUS_FIRST or event == EVT_ROT_RIGHT or event == EVT_PLUS_REPT then + addField(1) + elseif event == EVT_MINUS_FIRST or event == EVT_ROT_LEFT or event == EVT_MINUS_REPT then + addField(-1) + end + else + if event == EVT_MINUS_FIRST or event == EVT_ROT_LEFT then + selectField(1) + elseif event == EVT_PLUS_FIRST or event == EVT_ROT_RIGHT then + selectField(-1) + end + end + redrawFieldsPage() + return 0 +end + +local calibrationPositionsBitmaps = { "bmp/up.bmp", "bmp/down.bmp", "bmp/left.bmp", "bmp/right.bmp", "bmp/forward.bmp", "bmp/back.bmp" } + +local function runCalibrationPage(event) + fields = calibrationFields + if refreshIndex == #fields then + refreshIndex = 0 + end + lcd.clear() + lcd.drawScreenTitle("SxR", page, #pages) + if(calibrationStep < 6) then + lcd.drawText(0, 9, "Turn the SxR as shown", 0) + lcd.drawPixmap(10, 19, calibrationPositionsBitmaps[1 + calibrationStep]) + for index = 1, 3, 1 do + local field = fields[index] + lcd.drawText(80, 12+10*index, field[1], 0) + lcd.drawNumber(90, 12+10*index, field[4]/10, LEFT+PREC2) + end + + local attr = calibrationState == 0 and INVERS or 0 + lcd.drawText(0, 56, "Press [Enter] when ready", attr) + else + lcd.drawText(0, 9, "Calibration completed", 0) + lcd.drawPixmap(10, 19, "bmp/done.bmp") + lcd.drawText(0, 56, "Press [Exit] when ready", attr) + end + if calibrationStep > 6 and (event == EVT_ENTER_BREAK or event == EVT_EXIT_BREAK) then + return 2 + elseif event == EVT_ENTER_BREAK then + calibrationState = 1 + elseif event == EVT_EXIT_BREAK then + if calibrationStep > 0 then + calibrationStep = 0 + end + end + return 0 +end + +-- Init +local function init() + current, edit, refreshState, refreshIndex = 1, false, 0, 0 + pages = { + runWarningPage, + runCalibrationPage + } +end + +-- Main +local function run(event) + if event == nil then + error("Cannot be run as a model script!") + return 2 + elseif event == EVT_PAGE_BREAK then + selectPage(1) + elseif event == EVT_PAGE_LONG then + killEvents(event); + selectPage(-1) + end + + local result = pages[page](event) + refreshNext() + + return result +end + +return { init=init, run=run } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/SxR/SxR.lua opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/SxR/SxR.lua --- opentx-companion22-2.2.0~ppa02~xenial/radio/sdcard/taranis-x9/SxR/SxR.lua 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/sdcard/taranis-x9/SxR/SxR.lua 2017-12-17 16:22:27.000000000 +0000 @@ -0,0 +1,277 @@ +---- ######################################################################### +---- # # +---- # Copyright (C) OpenTX # +-----# # +---- # License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html # +---- # # +---- # This program is free software; you can redistribute it and/or modify # +---- # it under the terms of the GNU General Public License version 2 as # +---- # published by the Free Software Foundation. # +---- # # +---- # 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. # +---- # # +---- ######################################################################### +local VALUE = 0 +local COMBO = 1 + +local COLUMN_2 = 150 + +local edit = false +local page = 1 +local current = 1 +local refreshState = 0 +local refreshIndex = 0 +local pageOffset = 0 +local pages = {} +local fields = {} +local modifications = {} + +local configFields = { + {"Wing type:", COMBO, 0x80, nil, { "Normal", "Delta", "VTail" } }, + {"Mounting type:", COMBO, 0x81, nil, { "Horz", "Horz rev.", "Vert", "Vert rev." } }, +} + +local settingsFields = { + {"SxR functions:", COMBO, 0x9C, nil, { "Disable", "Enable" } }, + {"Quick Mode:", COMBO, 0xAA, nil, { "Disable", "Enable" } }, + {"CH5 mode:", COMBO, 0xA8, nil, { "AIL2", "AUX1" } }, + {"CH6 mode:", COMBO, 0xA9, nil, { "ELE2", "AUX2" } }, + {"AIL direction:", COMBO, 0x82, nil, { "Normal", "Invers" }, { 255, 0 } }, + {"ELE direction:", COMBO, 0x83, nil, { "Normal", "Invers" }, { 255, 0 } }, + {"RUD direction:", COMBO, 0x84, nil, { "Normal", "Invers" }, { 255, 0 } }, + {"AIL2 direction:", COMBO, 0x9A, nil, { "Normal", "Invers" }, { 255, 0 } }, + {"ELE2 direction:", COMBO, 0x9B, nil, { "Normal", "Invers" }, { 255, 0 } }, + {"AIL stabilize gain:", VALUE, 0x85, nil, 0, 200, "%"}, + {"ELE stabilize gain:", VALUE, 0x86, nil, 0, 200, "%"}, + {"RUD stabilize gain:", VALUE, 0x87, nil, 0, 200, "%"}, + {"AIL auto level gain:", VALUE, 0x88, nil, 0, 200, "%"}, + {"ELE auto level gain:", VALUE, 0x89, nil, 0, 200, "%"}, + {"ELE upright gain:", VALUE, 0x8C, nil, 0, 200, "%"}, + {"RUD upright gain:", VALUE, 0x8D, nil, 0, 200, "%"}, + {"AIL crab gain:", VALUE, 0x8E, nil, 0, 200, "%"}, + {"RUD crab gain:", VALUE, 0x90, nil, 0, 200, "%"}, + {"AIL auto angle offset:", VALUE, 0x91, nil, -20, 20, "%", 0x6C}, + {"ELE auto angle offset:", VALUE, 0x92, nil, -20, 20, "%", 0x6C}, + {"ELE upright angle offset:", VALUE, 0x95, nil, -20, 20, "%", 0x6C}, + {"RUD upright angle offset:", VALUE, 0x96, nil, -20, 20, "%", 0x6C}, + {"AIL crab angle offset:", VALUE, 0x97, nil, -20, 20, "%", 0x6C}, + {"RUD crab angle offset:", VALUE, 0x99, nil, -20, 20, "%", 0x6C}, +} + +-- Change display attribute to current field +local function addField(step) + local field = fields[current] + local min, max + if field[2] == VALUE then + min = field[5] + max = field[6] + elseif field[2] == COMBO then + min = 0 + max = #(field[5]) - 1 + end + if (step < 0 and field[4] > min) or (step > 0 and field[4] < max) then + field[4] = field[4] + step + end +end + +-- Select the next or previous page +local function selectPage(step) + page = 1 + ((page + step - 1 + #pages) % #pages) + refreshIndex = 0 + pageOffset = 0 +end + +-- Select the next or previous editable field +local function selectField(step) + current = 1 + ((current + step - 1 + #fields) % #fields) + if current > 7 + pageOffset then + pageOffset = current - 7 + elseif current <= pageOffset then + pageOffset = current - 1 + end +end + +local function drawProgressBar() + local width = (140 * refreshIndex) / #fields + lcd.drawRectangle(30, 1, 144, 6) + lcd.drawFilledRectangle(32, 3, width, 2); +end + +-- Redraw the current page +local function redrawFieldsPage() + lcd.clear() + lcd.drawScreenTitle("SxR", page, #pages) + + if refreshIndex < #fields then + drawProgressBar() + end + + for index = 1, 7, 1 do + local field = fields[pageOffset+index] + if field == nil then + break + end + + local attr = current == (pageOffset+index) and ((edit == true and BLINK or 0) + INVERS) or 0 + + lcd.drawText(0, 1+8*index, field[1]) + + if field[4] == nil then + lcd.drawText(COLUMN_2, 1+8*index, "---", attr) + else + if field[2] == VALUE then + lcd.drawNumber(COLUMN_2, 1+8*index, field[4], LEFT + attr) + elseif field[2] == COMBO then + if field[4] >= 0 and field[4] < #(field[5]) then + lcd.drawText(COLUMN_2, 1+8*index, field[5][1+field[4]], attr) + end + end + end + end +end + +local function telemetryRead(field) + return sportTelemetryPush(0x17, 0x30, 0x0C30, field) +end + +local function telemetryWrite(field, value) + return sportTelemetryPush(0x17, 0x31, 0x0C30, field + value*256) +end + +local telemetryPopTimeout = 0 +local function refreshNext() + if refreshState == 0 then + if #modifications > 0 then + telemetryWrite(modifications[1][1], modifications[1][2]) + modifications[1] = nil + elseif refreshIndex < #fields then + local field = fields[refreshIndex + 1] + if telemetryRead(field[3]) == true then + refreshState = 1 + telemetryPopTimeout = getTime() + 120 -- normal delay is 500ms + end + end + elseif refreshState == 1 then + local physicalId, primId, dataId, value = sportTelemetryPop() + if physicalId == 0x1A and primId == 0x32 and dataId == 0x0C30 then + local fieldId = value % 256 + local field = fields[refreshIndex + 1] + if fieldId == field[3] then + local value = math.floor(value / 256) + if field[3] >= 0x9E and field[3] <= 0xA0 then + local b1 = value % 256 + local b2 = math.floor(value / 256) + value = b1*256 + b2 + value = value - bit32.band(value, 0x8000) * 2 + end + if field[2] == COMBO and #field == 6 then + for index = 1, #(field[6]), 1 do + if value == field[6][index] then + value = index - 1 + break + end + end + elseif field[2] == VALUE and #field == 8 then + value = value - field[8] + field[5] + end + fields[refreshIndex + 1][4] = value + refreshIndex = refreshIndex + 1 + refreshState = 0 + end + elseif getTime() > telemetryPopTimeout then + fields[refreshIndex + 1][4] = nil + refreshIndex = refreshIndex + 1 + refreshState = 0 + end + end +end + +local function updateField(field) + local value = field[4] + if field[2] == COMBO and #field == 6 then + value = field[6][1+value] + elseif field[2] == VALUE and #field == 8 then + value = value + field[8] - field[5] + end + modifications[#modifications+1] = { field[3], value } +end + +-- Main +local function runFieldsPage(event) + if event == EVT_EXIT_BREAK then -- exit script + return 2 + elseif event == EVT_ENTER_BREAK then -- toggle editing/selecting current field + if fields[current][4] ~= nil then + edit = not edit + if edit == false then + updateField(fields[current]) + end + end + elseif edit then + if event == EVT_PLUS_FIRST or event == EVT_ROT_RIGHT or event == EVT_PLUS_REPT then + addField(1) + elseif event == EVT_MINUS_FIRST or event == EVT_ROT_LEFT or event == EVT_MINUS_REPT then + addField(-1) + end + else + if event == EVT_MINUS_FIRST or event == EVT_ROT_RIGHT then + selectField(1) + elseif event == EVT_PLUS_FIRST or event == EVT_ROT_LEFT then + selectField(-1) + end + end + redrawFieldsPage() + return 0 +end + +local wingBitmaps = { "bmp/plane.bmp", "bmp/delta.bmp", "bmp/vtail.bmp" } +local mountBitmaps = { "bmp/horz.bmp", "bmp/horz-r.bmp", "bmp/vert.bmp", "bmp/vert-r.bmp" } + +local function runConfigPage(event) + fields = configFields + local result = runFieldsPage(event) + if fields[1][4] ~= nil then + lcd.drawPixmap(20, 28, wingBitmaps[1 + fields[1][4]]) + end + if fields[2][4] ~= nil then + lcd.drawPixmap(128, 28, mountBitmaps[1 + fields[2][4]]) + end + return result +end + +local function runSettingsPage(event) + fields = settingsFields + return runFieldsPage(event) +end + +-- Init +local function init() + current, edit, refreshState, refreshIndex = 1, false, 0, 0 + pages = { + runConfigPage, + runSettingsPage, + } +end + +-- Main +local function run(event) + if event == nil then + error("Cannot be run as a model script!") + return 2 + elseif event == EVT_PAGE_BREAK then + selectPage(1) + elseif event == EVT_PAGE_LONG then + killEvents(event); + selectPage(-1) + end + + local result = pages[page](event) + refreshNext() + + return result +end + +return { init=init, run=run } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/audio_arm.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/audio_arm.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/audio_arm.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/audio_arm.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -180,6 +180,7 @@ "sensorko", "servoko", "rxko", + "modelpwr", #if defined(PCBSKY9X) "highmah", "hightemp", @@ -200,6 +201,10 @@ "midpot2", "midslid1", "midslid2", +#if defined(PCBX9E) + "midslid3", + "midslid4", +#endif #else "midpot1", "midpot2", @@ -820,9 +825,9 @@ bool AudioQueue::isPlaying(uint8_t id) { - return normalContext.hasId(id) || - (isFunctionActive(FUNCTION_BACKGND_MUSIC) && backgroundContext.hasId(id)) || - fragmentsFifo.hasId(id); + return normalContext.hasPromptId(id) || + (isFunctionActive(FUNCTION_BACKGND_MUSIC) && backgroundContext.hasPromptId(id)) || + fragmentsFifo.hasPromptId(id); } void AudioQueue::playTone(uint16_t freq, uint16_t len, uint16_t pause, uint8_t flags, int8_t freqIncr) @@ -858,7 +863,7 @@ } #if defined(SDCARD) -void AudioQueue::playFile(const char *filename, uint8_t flags, uint8_t id) +void AudioQueue::playFile(const char * filename, uint8_t flags, uint8_t id) { #if defined(SIMU) TRACE("playFile(\"%s\", flags=%x, id=%d)", filename, flags, id); @@ -871,7 +876,6 @@ #endif #endif - if (!sdMounted()) return; @@ -906,8 +910,12 @@ return; #endif - // For the moment it's only needed to stop the background music + CoEnterMutexSection(audioMutex); + + fragmentsFifo.removePromptById(id); backgroundContext.stop(id); + + CoLeaveMutexSection(audioMutex); } void AudioQueue::stopSD() @@ -1047,7 +1055,8 @@ #if defined(SDCARD) char filename[AUDIO_FILENAME_MAXLEN + 1]; if (index < AU_SPECIAL_SOUND_FIRST && isAudioFileReferenced(index, filename)) { - audioQueue.playFile(filename); + audioQueue.stopPlay(ID_PLAY_PROMPT_BASE + index); + audioQueue.playFile(filename, 0, ID_PLAY_PROMPT_BASE + index); return; } #endif @@ -1096,6 +1105,10 @@ #if defined(PCBTARANIS) || defined(PCBFLAMENCO) || defined(PCBHORUS) case AU_SLIDER1_MIDDLE: case AU_SLIDER2_MIDDLE: +#if defined(PCBX9E) + case AU_SLIDER3_MIDDLE: + case AU_SLIDER4_MIDDLE: +#endif #else case AU_POT3_MIDDLE: #endif @@ -1197,7 +1210,7 @@ { if (unit < DIM(unitsFilenames)) { char path[AUDIO_FILENAME_MAXLEN+1]; - char *tmp = strAppendSystemAudioPath(path); + char * tmp = strAppendSystemAudioPath(path); tmp = strAppendStringWithIndex(tmp, unitsFilenames[unit], idx); strcpy(tmp, SOUNDS_EXT); audioQueue.playFile(path, 0, id); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/audio_arm.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/audio_arm.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/audio_arm.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/audio_arm.h 2017-10-31 16:16:43.000000000 +0000 @@ -147,7 +147,6 @@ {}; }; - struct AudioFragment { uint8_t type; uint8_t id; @@ -209,7 +208,7 @@ inline void clear() { fragment.clear(); }; int mixBuffer(AudioBuffer *buffer, int volume, unsigned int fade); - bool hasId(uint8_t id) const { return fragment.id == id; }; + bool hasPromptId(uint8_t id) const { return fragment.id == id; }; void setFragment(const char * filename, uint8_t repeat, uint8_t id) { @@ -262,7 +261,7 @@ bool isEmpty() const { return fragment.type == FRAGMENT_EMPTY; }; bool isTone() const { return fragment.type == FRAGMENT_TONE; }; bool isFile() const { return fragment.type == FRAGMENT_FILE; }; - bool hasId(uint8_t id) const { return fragment.id == id; }; + bool hasPromptId(uint8_t id) const { return fragment.id == id; }; int mixBuffer(AudioBuffer *buffer, int toneVolume, int wavVolume, unsigned int fade) { @@ -414,7 +413,7 @@ public: AudioFragmentFifo() : ridx(0), widx(0), fragments() {}; - bool hasId(uint8_t id) + bool hasPromptId(uint8_t id) { uint8_t i = ridx; while (i != widx) { @@ -425,6 +424,17 @@ return false; } + bool removePromptById(uint8_t id) + { + uint8_t i = ridx; + while (i != widx) { + AudioFragment & fragment = fragments[i]; + if (fragment.id == id) fragment.clear(); + i = nextIdx(i); + } + return false; + } + bool empty() const { return ridx == widx; @@ -502,14 +512,17 @@ extern AudioQueue audioQueue; enum { - ID_PLAY_FROM_SD_MANAGER = 254, - ID_PLAY_BYE = 255 + // IDs for special functions [0:64] + // IDs for global functions [64:128] + ID_PLAY_PROMPT_BASE = 128, + ID_PLAY_FROM_SD_MANAGER = 255, }; void codecsInit(); void audioEvent(unsigned int index); void audioPlay(unsigned int index, uint8_t id=0); void audioStart(); +void audioTask(void * pdata); #if defined(AUDIO) && defined(BUZZER) #define AUDIO_BUZZER(a, b) do { a; b; } while(0) @@ -536,7 +549,7 @@ #define AUDIO_KEY_ERROR() audioKeyError() #define AUDIO_HELLO() audioPlay(AUDIO_HELLO) -#define AUDIO_BYE() audioPlay(AU_BYE, ID_PLAY_BYE) +#define AUDIO_BYE() audioPlay(AU_BYE, ID_PLAY_PROMPT_BASE + AU_BYE) #define AUDIO_WARNING1() AUDIO_BUZZER(audioEvent(AU_WARNING1), beep(3)) #define AUDIO_WARNING2() AUDIO_BUZZER(audioEvent(AU_WARNING2), beep(2)) #define AUDIO_TX_BATTERY_LOW() AUDIO_BUZZER(audioEvent(AU_TX_BATTERY_LOW), beep(4)) diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/bitmaps/128x64/CMakeLists.txt opentx-companion22-2.2.1~ppa01~xenial/radio/src/bitmaps/128x64/CMakeLists.txt --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/bitmaps/128x64/CMakeLists.txt 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/bitmaps/128x64/CMakeLists.txt 2017-10-31 16:16:43.000000000 +0000 @@ -1,4 +1,5 @@ +string(TOLOWER "${FONT}" FONT_DIR) add_bitmaps_target(9x_xbm_1bit ${RADIO_SRC_DIRECTORY}/bitmaps/sticks.xbm 128 1bit 4) -add_bitmaps_target(9x_fonts_1bit ${RADIO_SRC_DIRECTORY}/fonts/std/*.png 128 "") +add_bitmaps_target(9x_fonts_1bit ${RADIO_SRC_DIRECTORY}/fonts/${FONT_DIR}/*.png 128 "") add_bitmaps_target(9x_bitmaps ${RADIO_SRC_DIRECTORY}/bitmaps/128x64/*.png 128 1bit) add_dependencies(9x_bitmaps 9x_fonts_1bit 9x_xbm_1bit) Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/src/bitmaps/128x64/sleep.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/src/bitmaps/128x64/sleep.png differ diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/bitmaps/212x64/CMakeLists.txt opentx-companion22-2.2.1~ppa01~xenial/radio/src/bitmaps/212x64/CMakeLists.txt --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/bitmaps/212x64/CMakeLists.txt 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/bitmaps/212x64/CMakeLists.txt 2017-10-31 16:16:43.000000000 +0000 @@ -1,4 +1,5 @@ +string(TOLOWER "${FONT}" FONT_DIR) add_bitmaps_target(taranis_xbm ${RADIO_SRC_DIRECTORY}/bitmaps/sticks.xbm 128 1bit 4) -add_bitmaps_target(taranis_fonts ${RADIO_SRC_DIRECTORY}/fonts/std/*.png 128 "") +add_bitmaps_target(taranis_fonts ${RADIO_SRC_DIRECTORY}/fonts/${FONT_DIR}/*.png 128 "") add_bitmaps_target(taranis_bitmaps ${RADIO_SRC_DIRECTORY}/bitmaps/212x64/*.png 212 4bits) add_dependencies(taranis_bitmaps taranis_fonts taranis_xbm) diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/bluetooth.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/bluetooth.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/bluetooth.cpp 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/bluetooth.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -0,0 +1,443 @@ +/* + * Copyright (C) OpenTX + * + * Based on code named + * th9x - http://code.google.com/p/th9x + * er9x - http://code.google.com/p/er9x + * gruvin9x - http://code.google.com/p/gruvin9x + * + * License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + * + * 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. + */ + +#include "opentx.h" + +#if defined(PCBX7) || defined(PCBHORUS) || defined(USEHORUSBT) +#define BLUETOOTH_COMMAND_NAME "AT+NAME" +#define BLUETOOTH_ANSWER_NAME "OK+" +#define BLUETOOTH_COMMAND_BAUD_115200 "AT+BAUD115200" +#else +#define BLUETOOTH_COMMAND_NAME "TTM:REN-" +#define BLUETOOTH_ANSWER_NAME "TTM:REN" +#define BLUETOOTH_COMMAND_BAUD_115200 "TTM:BPS-115200" +#endif + +#define BLUETOOTH_PACKET_SIZE 14 +#define BLUETOOTH_LINE_LENGTH 32 + +extern Fifo btTxFifo; +extern Fifo btRxFifo; + +volatile uint8_t bluetoothState; +char bluetoothLocalAddr[LEN_BLUETOOTH_ADDR+1]; +char bluetoothDistantAddr[LEN_BLUETOOTH_ADDR+1]; +uint8_t bluetoothBuffer[BLUETOOTH_LINE_LENGTH+1]; +uint8_t bluetoothBufferIndex = 0; +tmr10ms_t bluetoothWakeupTime = 0; + +void bluetoothWrite(const uint8_t * data, uint8_t length) +{ + TRACE_NOCRLF("BT>"); + for (int i=0; i %s", str); + while (*str != 0) { + btTxFifo.push(*str++); + } + bluetoothWriteWakeup(); +} + +char * bluetoothReadline(bool error_reset) +{ + uint8_t byte; + + while (1) { + if (!btRxFifo.pop(byte)) { +#if defined(PCBX9E) && !defined(USEHORUSBT) // X9E BT module can get unresponsive + TRACE("NO RESPONSE FROM BT MODULE"); +#endif + return NULL; + } + TRACE_NOCRLF("%02X ", byte); + if (byte == '\n') { + if (bluetoothBufferIndex > 2 && bluetoothBuffer[bluetoothBufferIndex-1] == '\r') { + bluetoothBuffer[bluetoothBufferIndex-1] = '\0'; + bluetoothBufferIndex = 0; + TRACE("BT< %s", bluetoothBuffer); + if (error_reset && !strcmp((char *)bluetoothBuffer, "ERROR")) { +#if defined(PCBX9E) // X9E enter BT reset loop if following code is implemented + TRACE("BT error..."); +#else + TRACE("BT Reset..."); + bluetoothDone(); + bluetoothState = BLUETOOTH_STATE_OFF; + bluetoothWakeupTime = get_tmr10ms() + 100; /* 1s */ +#endif + return NULL; + } + else { + if (!strncmp((char *)bluetoothBuffer, "Central:", 8)) + strcpy(bluetoothLocalAddr, (char *)bluetoothBuffer+8); + else if (!strncmp((char *)bluetoothBuffer, "Peripheral:", 11)) + strcpy(bluetoothLocalAddr, (char *)bluetoothBuffer+11); + return (char *)bluetoothBuffer; + } + } + else { + bluetoothBufferIndex = 0; + } + } + else { + bluetoothBuffer[bluetoothBufferIndex++] = byte; + bluetoothBufferIndex &= (BLUETOOTH_LINE_LENGTH-1); + } + } +} + +void bluetoothProcessTrainerFrame(const uint8_t * bluetoothBuffer) +{ + TRACE(""); + + for (uint8_t channel=0, i=1; channel<8; channel+=2, i+=3) { + // +-500 != 512, but close enough. + ppmInput[channel] = bluetoothBuffer[i] + ((bluetoothBuffer[i+1] & 0xf0) << 4) - 1500; + ppmInput[channel+1] = ((bluetoothBuffer[i+1] & 0x0f) << 4) + ((bluetoothBuffer[i+2] & 0xf0) >> 4) + ((bluetoothBuffer[i+2] & 0x0f) << 8) - 1500; + } + + ppmInputValidityTimer = PPM_IN_VALID_TIMEOUT; +} + +void bluetoothAppendTrainerByte(uint8_t data) +{ + if (bluetoothBufferIndex < BLUETOOTH_LINE_LENGTH) { + bluetoothBuffer[bluetoothBufferIndex++] = data; + // we check for "DisConnected", but the first byte could be altered (if received in state STATE_DATA_XOR) + if (data == '\n') { + if (!strncmp((char *)&bluetoothBuffer[bluetoothBufferIndex-13], "isConnected", 11)) { + TRACE("BT< DisConnected"); + bluetoothState = BLUETOOTH_STATE_DISCONNECTED; + bluetoothBufferIndex = 0; + bluetoothWakeupTime += 200; // 1s + } + } + } +} + +void bluetoothProcessTrainerByte(uint8_t data) +{ + static uint8_t dataState = STATE_DATA_IDLE; + + switch (dataState) { + case STATE_DATA_START: + if (data == START_STOP) { + dataState = STATE_DATA_IN_FRAME ; + bluetoothBufferIndex = 0; + } + else { + bluetoothAppendTrainerByte(data); + } + break; + + case STATE_DATA_IN_FRAME: + if (data == BYTESTUFF) { + dataState = STATE_DATA_XOR; // XOR next byte + } + else if (data == START_STOP) { + dataState = STATE_DATA_IN_FRAME ; + bluetoothBufferIndex = 0; + } + else { + bluetoothAppendTrainerByte(data); + } + break; + + case STATE_DATA_XOR: + bluetoothAppendTrainerByte(data ^ STUFF_MASK); + dataState = STATE_DATA_IN_FRAME; + break; + + case STATE_DATA_IDLE: + if (data == START_STOP) { + bluetoothBufferIndex = 0; + dataState = STATE_DATA_START; + } + else { + bluetoothAppendTrainerByte(data); + } + break; + } + + if (bluetoothBufferIndex >= BLUETOOTH_PACKET_SIZE) { + uint8_t crc = 0x00; + for (int i=0; i<13; i++) { + crc ^= bluetoothBuffer[i]; + } + if (crc == bluetoothBuffer[13]) { + if (bluetoothBuffer[0] == 0x80) { + bluetoothProcessTrainerFrame(bluetoothBuffer); + } + } + dataState = STATE_DATA_IDLE; + } +} + +uint8_t bluetoothCrc; +void bluetoothPushByte(uint8_t byte) +{ + bluetoothCrc ^= byte; + if (byte == START_STOP || byte == BYTESTUFF) { + bluetoothBuffer[bluetoothBufferIndex++] = 0x7d; + byte ^= STUFF_MASK; + } + bluetoothBuffer[bluetoothBufferIndex++] = byte; +} + +void bluetoothSendTrainer() +{ + int16_t PPM_range = g_model.extendedLimits ? 640*2 : 512*2; + + int firstCh = g_model.moduleData[TRAINER_MODULE].channelsStart; + int lastCh = firstCh + 8; + + uint8_t * cur = bluetoothBuffer; + bluetoothBufferIndex = 0; + bluetoothCrc = 0x00; + + bluetoothBuffer[bluetoothBufferIndex++] = START_STOP; // start byte + bluetoothPushByte(0x80); // trainer frame type? + for (int channel=0; channel> 4) + ((channelValue2 & 0x00f0) >> 4)); + bluetoothPushByte(((channelValue2 & 0x000f) << 4) + ((channelValue2 & 0x0f00) >> 8)); + } + bluetoothBuffer[bluetoothBufferIndex++] = bluetoothCrc; + bluetoothBuffer[bluetoothBufferIndex++] = START_STOP; // end byte + + bluetoothWrite(bluetoothBuffer, bluetoothBufferIndex); + bluetoothBufferIndex = 0; +} + +void bluetoothForwardTelemetry(uint8_t data) +{ + bluetoothBuffer[bluetoothBufferIndex++] = data; + if (data == START_STOP && bluetoothBufferIndex >= 2*FRSKY_SPORT_PACKET_SIZE) { + bluetoothWrite(bluetoothBuffer, bluetoothBufferIndex); + bluetoothBufferIndex = 0; + } +} + +void bluetoothReceiveTrainer() +{ + uint8_t byte; + + while (1) { + if (!btRxFifo.pop(byte)) { + return; + } + + TRACE_NOCRLF("%02X ", byte); + + bluetoothProcessTrainerByte(byte); + } +} + +#if defined(PCBX9E) && !defined(USEHORUSBT) +void bluetoothWakeup(void) +{ + if (!g_eeGeneral.bluetoothMode) { + if (bluetoothState != BLUETOOTH_INIT) { + bluetoothDone(); + bluetoothState = BLUETOOTH_INIT; + } + } + else { + static tmr10ms_t waitEnd = 0; + if (bluetoothState != BLUETOOTH_STATE_IDLE) { + + if (bluetoothState == BLUETOOTH_INIT) { + bluetoothInit(BLUETOOTH_DEFAULT_BAUDRATE); + char command[32]; + char * cur = strAppend(command, BLUETOOTH_COMMAND_NAME); + uint8_t len = ZLEN(g_eeGeneral.bluetoothName); + if (len > 0) { + for (int i = 0; i < len; i++) { + *cur++ = idx2char(g_eeGeneral.bluetoothName[i]); + } + } + else { + cur = strAppend(cur, "Taranis-X9E"); + } + strAppend(cur, "\r\n"); + bluetoothWriteString(command); + bluetoothState = BLUETOOTH_WAIT_TTM; + waitEnd = get_tmr10ms() + 25; // 250ms + } + else if (bluetoothState == BLUETOOTH_WAIT_TTM) { + if (get_tmr10ms() > waitEnd) { + char * line = bluetoothReadline(); + if (strncmp(line, "OK+", 3)) { + bluetoothState = BLUETOOTH_STATE_IDLE; + } + else { + bluetoothInit(BLUETOOTH_FACTORY_BAUDRATE); + const char btMessage[] = "TTM:BPS-115200"; + bluetoothWriteString(btMessage); + bluetoothState = BLUETOOTH_WAIT_BAUDRATE_CHANGE; + waitEnd = get_tmr10ms() + 250; // 2.5s + } + } + } + else if (bluetoothState == BLUETOOTH_WAIT_BAUDRATE_CHANGE) { + if (get_tmr10ms() > waitEnd) { + bluetoothState = BLUETOOTH_INIT; + } + } + } + else if (IS_BLUETOOTH_TRAINER()){ + bluetoothState = BLUETOOTH_STATE_CONNECTED; + bluetoothWriteWakeup(); + bluetoothSendTrainer(); + } + } +} +#else // PCBX9E +void bluetoothWakeup() +{ + tmr10ms_t now = get_tmr10ms(); + + if (now < bluetoothWakeupTime) + return; + + bluetoothWakeupTime = now + 5; /* 50ms default */ + + if (g_eeGeneral.bluetoothMode == BLUETOOTH_OFF || (g_eeGeneral.bluetoothMode == BLUETOOTH_TRAINER && !IS_BLUETOOTH_TRAINER())) { + if (bluetoothState != BLUETOOTH_STATE_OFF) { + bluetoothDone(); + bluetoothState = BLUETOOTH_STATE_OFF; + } + bluetoothWakeupTime = now + 10; /* 100ms */ + } + else if (bluetoothState == BLUETOOTH_STATE_OFF) { + bluetoothInit(BLUETOOTH_FACTORY_BAUDRATE); + bluetoothState = BLUETOOTH_STATE_FACTORY_BAUDRATE_INIT; + } + + if (bluetoothState != BLUETOOTH_STATE_OFF) { + bluetoothWriteWakeup(); + if (bluetoothIsWriting()) { + return; + } + } + + if (bluetoothState == BLUETOOTH_STATE_FACTORY_BAUDRATE_INIT) { + bluetoothWriteString("AT+BAUD4\r\n"); + bluetoothState = BLUETOOTH_STATE_BAUDRATE_SENT; + bluetoothWakeupTime = now + 10; /* 100ms */ + } + else if (bluetoothState == BLUETOOTH_STATE_BAUDRATE_SENT) { + bluetoothInit(BLUETOOTH_DEFAULT_BAUDRATE); + bluetoothState = BLUETOOTH_STATE_BAUDRATE_INIT; + bluetoothReadline(false); + bluetoothWakeupTime = now + 10; /* 100ms */ + } + else if (bluetoothState == BLUETOOTH_STATE_CONNECTED) { + if (g_eeGeneral.bluetoothMode == BLUETOOTH_TRAINER && g_model.trainerMode == TRAINER_MODE_MASTER_BLUETOOTH) { + bluetoothReceiveTrainer(); + } + else { + if (g_eeGeneral.bluetoothMode == BLUETOOTH_TRAINER && g_model.trainerMode == TRAINER_MODE_SLAVE_BLUETOOTH) { + bluetoothSendTrainer(); + bluetoothWakeupTime = now + 2; /* 20ms */ + } + bluetoothReadline(); // to deal with "ERROR" + } + } + else { + char * line = bluetoothReadline(); + if (bluetoothState == BLUETOOTH_STATE_BAUDRATE_INIT) { + char command[32]; + char * cur = strAppend(command, BLUETOOTH_COMMAND_NAME); + uint8_t len = ZLEN(g_eeGeneral.bluetoothName); + if (len > 0) { + for (int i = 0; i < len; i++) { + *cur++ = idx2char(g_eeGeneral.bluetoothName[i]); + } + } + else { +#if defined(PCBHORUS) + cur = strAppend(cur, "Horus"); +#else + cur = strAppend(cur, "Taranis"); +#endif + } + strAppend(cur, "\r\n"); + bluetoothWriteString(command); + bluetoothState = BLUETOOTH_STATE_NAME_SENT; + } + else if (bluetoothState == BLUETOOTH_STATE_NAME_SENT && (!strncmp(line, "OK+", 3) || !strncmp(line, "Central:", 8) || !strncmp(line, "Peripheral:", 11))) { + bluetoothWriteString("AT+TXPW3\r\n"); + bluetoothState = BLUETOOTH_STATE_POWER_SENT; + } + else if (bluetoothState == BLUETOOTH_STATE_POWER_SENT && (!strncmp(line, "Central:", 8) || !strncmp(line, "Peripheral:", 11))) { + if (g_eeGeneral.bluetoothMode == BLUETOOTH_TRAINER && g_model.trainerMode == TRAINER_MODE_MASTER_BLUETOOTH) + bluetoothWriteString("AT+ROLE1\r\n"); + else + bluetoothWriteString("AT+ROLE0\r\n"); + bluetoothState = BLUETOOTH_STATE_ROLE_SENT; + } + else if (bluetoothState == BLUETOOTH_STATE_ROLE_SENT && (!strncmp(line, "Central:", 8) || !strncmp(line, "Peripheral:", 11))) { + bluetoothState = BLUETOOTH_STATE_IDLE; + } + else if (bluetoothState == BLUETOOTH_STATE_DISCOVER_REQUESTED) { + bluetoothWriteString("AT+DISC?\r\n"); + bluetoothState = BLUETOOTH_STATE_DISCOVER_SENT; + } + else if (bluetoothState == BLUETOOTH_STATE_DISCOVER_SENT && !strcmp(line, "OK+DISCS")) { + bluetoothState = BLUETOOTH_STATE_DISCOVER_START; + } + else if (bluetoothState == BLUETOOTH_STATE_DISCOVER_START && !strncmp(line, "OK+DISC:", 8)) { + strcpy(bluetoothDistantAddr, &line[8]); // TODO quick & dirty + } + else if (bluetoothState == BLUETOOTH_STATE_DISCOVER_START && !strcmp(line, "OK+DISCE")) { + bluetoothState = BLUETOOTH_STATE_DISCOVER_END; + } + else if (bluetoothState == BLUETOOTH_STATE_BIND_REQUESTED) { + char command[32]; + strAppend(strAppend(strAppend(command, "AT+CON"), bluetoothDistantAddr), "\r\n"); + bluetoothWriteString(command); + bluetoothState = BLUETOOTH_STATE_CONNECT_SENT; + } + else if ((bluetoothState == BLUETOOTH_STATE_IDLE || bluetoothState == BLUETOOTH_STATE_DISCONNECTED || bluetoothState == BLUETOOTH_STATE_CONNECT_SENT) && !strncmp(line, "Connected:", 10)) { + strcpy(bluetoothDistantAddr, &line[10]); // TODO quick & dirty + bluetoothState = BLUETOOTH_STATE_CONNECTED; + if (g_model.trainerMode == TRAINER_MODE_SLAVE_BLUETOOTH) { + bluetoothWakeupTime += 500; // it seems a 5s delay is needed before sending the 1st frame + } + } + else if (bluetoothState == BLUETOOTH_STATE_DISCONNECTED && !line) { + char command[32]; + strAppend(strAppend(strAppend(command, "AT+CON"), bluetoothDistantAddr), "\r\n"); + bluetoothWriteString(command); + bluetoothWakeupTime = now + 200; /* 2s */ + } + } +} +#endif diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/bluetooth.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/bluetooth.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/bluetooth.h 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/bluetooth.h 2017-11-20 18:44:06.000000000 +0000 @@ -0,0 +1,58 @@ +/* + * Copyright (C) OpenTX + * + * Based on code named + * th9x - http://code.google.com/p/th9x + * er9x - http://code.google.com/p/er9x + * gruvin9x - http://code.google.com/p/gruvin9x + * + * License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + * + * 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. + */ + +enum BluetoothStates { +#if defined(PCBX9E) && !defined(USEHORUSBT) + BLUETOOTH_INIT, + BLUETOOTH_WAIT_TTM, + BLUETOOTH_WAIT_BAUDRATE_CHANGE, +#endif + BLUETOOTH_STATE_OFF, + BLUETOOTH_STATE_FACTORY_BAUDRATE_INIT, + BLUETOOTH_STATE_BAUDRATE_SENT, + BLUETOOTH_STATE_BAUDRATE_INIT, + BLUETOOTH_STATE_NAME_SENT, + BLUETOOTH_STATE_POWER_SENT, + BLUETOOTH_STATE_ROLE_SENT, + BLUETOOTH_STATE_IDLE, + BLUETOOTH_STATE_DISCOVER_REQUESTED, + BLUETOOTH_STATE_DISCOVER_SENT, + BLUETOOTH_STATE_DISCOVER_START, + BLUETOOTH_STATE_DISCOVER_END, + BLUETOOTH_STATE_BIND_REQUESTED, + BLUETOOTH_STATE_CONNECT_SENT, + BLUETOOTH_STATE_CONNECTED, + BLUETOOTH_STATE_DISCONNECTED, +}; + +#define LEN_BLUETOOTH_ADDR 16 + +#if defined(PCBX7) +extern uint8_t btChipPresent; +#endif + +extern volatile uint8_t bluetoothState; +extern char bluetoothLocalAddr[LEN_BLUETOOTH_ADDR+1]; +extern char bluetoothDistantAddr[LEN_BLUETOOTH_ADDR+1]; + +char * bluetoothReadline(bool error_reset=true); +void bluetoothWriteString(const char * command); +void bluetoothForwardTelemetry(uint8_t data); +void bluetoothWakeup(); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/cli.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/cli.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/cli.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/cli.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -858,11 +858,6 @@ else if (audioTaskId == n) { serialPrint("%d: audio", n); } -#if defined(BLUETOOTH) - else if (btTaskId == n) { - serialPrint("%d: BT", n); - } -#endif } serialCrlf(); @@ -1181,7 +1176,7 @@ int cliGps(const char ** argv) { int baudrate = 0; - + if (argv[1][0] == '$') { // send command to GPS gpsSendFrame(argv[1]); @@ -1206,28 +1201,18 @@ int cliBlueTooth(const char ** argv) { int baudrate = 0; - if (argv[1][0] == '$') { - // send command to GPS - bluetoothWriteString(argv[1] + 1); - bluetoothWriteString("\r\n"); - serialPrint("bt sent: %s", argv[1] + 1); - CoTickDelay(100); // 200ms - char buff[100]; - int len = bluetoothRead(buff, 100); - buff[len] = 0; - serialPrint("bt read: %s", buff); - - } - else if (!strcmp(argv[1], "read")) { - char buff[100]; - int len = bluetoothRead(buff, 100); - buff[len] = 0; - serialPrint("bt read: %s", buff); + if (!strncmp(argv[1], "AT", 2) || !strncmp(argv[1], "TTM", 3)) { + char command[32]; + strAppend(strAppend(command, argv[1]), "\r\n"); + bluetoothWriteString(command); + char * line = bluetoothReadline(); + serialPrint(" 0) { if (baudrate > 0) { bluetoothInit(baudrate); - serialPrint("BT baudrate set to %d", baudrate); + char * line = bluetoothReadline(); + serialPrint("] []" }, @@ -1270,7 +1255,7 @@ { "gps", cliGps, "|$|trace" }, #endif #if defined(BLUETOOTH) - { "bt", cliBlueTooth, "|$|read" }, + { "bt", cliBlueTooth, "|" }, #endif { NULL, NULL, NULL } /* sentinel */ }; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/CMakeLists.txt opentx-companion22-2.2.1~ppa01~xenial/radio/src/CMakeLists.txt --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/CMakeLists.txt 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/CMakeLists.txt 2017-12-17 16:22:27.000000000 +0000 @@ -3,7 +3,7 @@ set(PCB_TYPES X7 X9D X9D+ X9E X10 X12S 9X 9XR 9X128 9XR128 9X2561 GRUVIN9X MEGA2560 SKY9X 9XRPRO AR9X) set(GUI_LANGUAGES CZ DE EN ES FR IT PT SK SE PL HU NL) -set(TTS_LANGUAGES CZ DE EN ES FR IT PT SK SE PL HU) +set(TTS_LANGUAGES CZ DE EN ES FR IT PT SK SE PL HU RU) set(PCB "X9D+" CACHE STRING "Radio type, one of: ${PCB_TYPES}") set_property(CACHE PCB PROPERTY STRINGS ${PCB_TYPES}) @@ -14,6 +14,8 @@ set(PPM_UNIT "PERCENT_PREC1" CACHE STRING "PPM display unit (US/PERCENT_PREC1/PERCENT_PREC0)") set_property(CACHE PPM_UNIT PROPERTY STRINGS US PERCENT_PREC1 PERCENT_PREC0) set(DEFAULT_MODE "" CACHE STRING "Default sticks mode") +set(FONT "STD" CACHE STRING "Choose font : STD or SQT5") +set_property(CACHE FONT PROPERTY STRINGS SQT5) option(HELI "Heli menu" ON) option(FLIGHT_MODES "Flight Modes" ON) @@ -39,7 +41,10 @@ option(TEMPLATES "Model templates menu" OFF) option(TRACE_SIMPGMSPACE "Turn on traces in simpgmspace.cpp" ON) option(TRACE_LUA_INTERNALS "Turn on traces for Lua internals" OFF) -option(BINDING_OPTIONS "Allow advanced frsky bindings" OFF) +option(FRSKY_STICKS "Reverse sticks for FrSky sticks" OFF) +option(NANO "Use nano newlib and binalloc") +option(NIGHTLY_BUILD_WARNING "Warn this is a nightly build" OFF) +option(USEHORUSBT "X9E BT module replaced by Horus BT module" OFF) # since we reset all default CMAKE compiler flags for firmware builds, provide an alternate way for user to specify additional flags. set(FIRMWARE_C_FLAGS "" CACHE STRING "Additional flags for firmware target c compiler (note: all CMAKE_C_FLAGS[_*] are ignored for firmware/bootloader).") @@ -47,15 +52,6 @@ set(FIRMWARE_CXX_FLAGS "" CACHE STRING "Additional flags for firmware target c++ compiler (note: all CMAKE_CXX_FLAGS[_*] are ignored for firmware/bootloader).") set(FIRMWARE_CXX_FLAGS_DEBUG "-g" CACHE STRING "Additional flags for firmware target (Debug config) c++ compiler (note: CMAKE_CXX_FLAGS_DEBUG is ignored for firmware/bootloader).") -# Python check -find_package("PythonInterp") -if(PYTHONINTERP_FOUND) - message(STATUS "Python found, version: ${PYTHON_VERSION_STRING}") -else() - message(WARNING "Python not found! Most firmware and simu flavors not buildable.") - set(LUA NO) -endif() - set(THIRDPARTY_DIR thirdparty) set(LUA_DIR ${THIRDPARTY_DIR}/Lua/src) set(COOS_DIR ${THIRDPARTY_DIR}/CoOS) @@ -198,6 +194,9 @@ if(LUA_COMPILER) add_definitions(-DLUA_COMPILER) endif() + if(LUA_ALLOCATOR_TRACER AND DEBUG) + add_definitions(-DLUA_ALLOCATOR_TRACER) + endif() if(NOT "${LUA_SCRIPT_LOAD_MODE}" STREQUAL "") add_definitions(-DLUA_SCRIPT_LOAD_MODE="${LUA_SCRIPT_LOAD_MODE}") endif() @@ -327,14 +326,26 @@ add_definitions(-DTRACE_LUA_INTERNALS_ENABLED) endif() -if(BINDING_OPTIONS) - add_definitions(-DBINDING_OPTIONS) +if(FRSKY_STICKS) + add_definitions(-DFRSKY_STICKS) +endif() + +if(NOT FONT STREQUAL "") + add_definitions(-DFONT=${DEFAULT_MODE}) endif() if(EEPROM_VARIANT_NEEDED) add_definitions(-DEEPROM_VARIANT=${EEPROM_VARIANT}) endif() +if(NIGHTLY_BUILD_WARNING) + add_definitions(-DNIGHTLY_BUILD_WARNING) +endif(NIGHTLY_BUILD_WARNING) + +if(USEHORUSBT) + add_definitions(-DUSEHORUSBT) +endif(USEHORUSBT) + set(SRC ${SRC} opentx.cpp @@ -462,6 +473,18 @@ add_definitions(-DSEMIHOSTING) set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} --specs=rdimon.specs") endif() + # Use newlib nano, which saves a few kilobytes. + if(NOT NANO STREQUAL NO) + set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} --specs=nano.specs") + if(NOT LUA STREQUAL NO) + # Lua needs %g and %f + set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} -u _printf_float -u _scanf_float") + endif() + # Nano's malloc does work well with lua, use our own + add_definitions(-DUSE_BIN_ALLOCATOR) + set(SRC ${SRC} bin_allocator.cpp) + endif() + if(PCB STREQUAL X9D OR PCB STREQUAL X9D+ OR PCB STREQUAL X9E OR PCB STREQUAL X7) add_subdirectory(targets/${TARGET_DIR}/bootloader) diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/dataconstants.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/dataconstants.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/dataconstants.h 2017-05-31 19:49:19.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/dataconstants.h 2017-10-31 16:16:43.000000000 +0000 @@ -287,6 +287,10 @@ TRAINER_MODE_MASTER_CPPM_EXTERNAL_MODULE, #endif TRAINER_MODE_MASTER_BATTERY_COMPARTMENT, +#if defined(BLUETOOTH) + TRAINER_MODE_MASTER_BLUETOOTH, + TRAINER_MODE_SLAVE_BLUETOOTH, +#endif }; #elif defined(PCBSKY9X) enum ModuleIndex { @@ -296,15 +300,21 @@ }; #endif -#if defined(PCBTARANIS) || defined(PCBHORUS) -#if defined(TARANIS_INTERNAL_PPM) - #define IS_INTERNAL_MODULE_ENABLED() (!(g_model.moduleData[INTERNAL_MODULE].rfProtocol == RF_PROTO_OFF && g_model.moduleData[INTERNAL_MODULE].type == MODULE_TYPE_XJT) && (g_model.moduleData[INTERNAL_MODULE].type != MODULE_TYPE_NONE)) +#if defined(BLUETOOTH) + #define TRAINER_MODE_MAX() TRAINER_MODE_SLAVE_BLUETOOTH +#elif defined(PCBX7) + #define TRAINER_MODE_MAX() TRAINER_MODE_MASTER_CPPM_EXTERNAL_MODULE #else - #define IS_INTERNAL_MODULE_ENABLED() (g_model.moduleData[INTERNAL_MODULE].rfProtocol != RF_PROTO_OFF) + #define TRAINER_MODE_MAX() HAS_WIRELESS_TRAINER_HARDWARE() ? TRAINER_MODE_MASTER_BATTERY_COMPARTMENT : TRAINER_MODE_MASTER_CPPM_EXTERNAL_MODULE #endif + +#if defined(PCBTARANIS) || defined(PCBHORUS) +#define IS_INTERNAL_MODULE_ENABLED() (g_model.moduleData[INTERNAL_MODULE].type != MODULE_TYPE_NONE) #elif defined(PCBSKY9X) #define IS_INTERNAL_MODULE_ENABLED() (false) #endif +#define IS_EXTERNAL_MODULE_ENABLED() (g_model.moduleData[EXTERNAL_MODULE].type != MODULE_TYPE_NONE) + enum UartModes { #if defined(CLI) || defined(DEBUG) @@ -509,8 +519,6 @@ #define MAX_TELEMETRY_SCREENS 4 #define TELEMETRY_SCREEN_TYPE(screenIndex) TelemetryScreenType((g_model.frsky.screensType >> (2*(screenIndex))) & 0x03) #define IS_BARS_SCREEN(screenIndex) (TELEMETRY_SCREEN_TYPE(screenIndex) == TELEMETRY_SCREEN_TYPE_GAUGES) -#define MIN_BLADES -1 // 1 blade -#define MAX_BLADES 126 // 128 blades #else #define MAX_FRSKY_A_CHANNELS 2 #define MAX_TELEMETRY_SCREENS 2 @@ -1054,4 +1062,10 @@ FUNC_ADJUST_GVAR_INCDEC, }; +enum BluetoothModes { + BLUETOOTH_OFF, + BLUETOOTH_TELEMETRY, + BLUETOOTH_TRAINER, +}; + #endif // _DATACONSTANTS_H_ diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/datastructs.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/datastructs.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/datastructs.h 2017-05-31 19:49:19.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/datastructs.h 2017-12-17 16:22:27.000000000 +0000 @@ -468,11 +468,22 @@ /* * Frsky Telemetry structure */ - +#if defined(CPUARM) +PACK(struct RssiAlarmData { + int8_t disabled:1; + int8_t spare:1; + int8_t warning:6; + int8_t spare2:2; + int8_t critical:6; + inline int8_t getWarningRssi() {return 45 + warning;} + inline int8_t getCriticalRssi() {return 42 + critical;} + }); +#else PACK(struct FrSkyRSSIAlarm { int8_t level:2; int8_t value:6; }); +#endif #if defined(CPUARM) typedef int16_t ls_telemetry_value_t; @@ -508,27 +519,15 @@ #endif #if defined(COLORLCD) -PACK(struct FrSkyTelemetryData { +PACK(struct FrSkyTelemetryData { // TODO EEPROM change, rename to VarioData uint8_t varioSource:7; uint8_t varioCenterSilent:1; int8_t varioCenterMax; int8_t varioCenterMin; int8_t varioMin; int8_t varioMax; - FrSkyRSSIAlarm rssiAlarms[2]; }); #elif defined(CPUARM) -PACK(struct FrSkyChannelData { - uint8_t ratio; // 0.0 means not used, 0.1V steps EG. 6.6 Volts = 66. 25.1V = 251, etc. - int16_t offset:12; - uint16_t type:4; // channel unit (0=volts, ...) - uint8_t alarms_value[2]; // 0.1V steps EG. 6.6 Volts = 66. 25.1V = 251, etc. - uint8_t alarms_level:4; - uint8_t alarms_greater:2; // 0=LT(<), 1=GT(>) - uint8_t spare:2; - uint8_t multiplier; // 0=no multiplier, 1=*2 multiplier -}); - // TODO remove this also on Taranis PACK(struct FrSkyTelemetryData { uint8_t voltsSource; @@ -541,7 +540,6 @@ int8_t varioCenterMin; int8_t varioMin; int8_t varioMax; - FrSkyRSSIAlarm rssiAlarms[2]; }); #else PACK(struct FrSkyChannelData { @@ -656,7 +654,7 @@ int8_t rfProtocol:4; uint8_t channelsStart; int8_t channelsCount; // 0=8 channels - uint8_t failsafeMode:4; //only 3 bits used + uint8_t failsafeMode:4; // only 3 bits used uint8_t subType:3; uint8_t invertedSerial:1; // telemetry serial inverted from standard int16_t failsafeChannels[MAX_OUTPUT_CHANNELS]; @@ -669,20 +667,27 @@ } ppm; NOBACKUP(struct { uint8_t rfProtocolExtra:2; - uint8_t spare:3; + uint8_t spare1:3; uint8_t customProto:1; uint8_t autoBindMode:1; uint8_t lowPowerMode:1; int8_t optionValue; } multi); NOBACKUP(struct { - uint8_t spare:4; + uint8_t power:2; // 0=10 mW, 1=100 mW, 2=500 mW, 3=1W + uint8_t spare1:2; uint8_t receiver_telem_off:1; // false = receiver telem enabled uint8_t receiver_channel_9_16:1; // false = pwm out 1-8, true 9-16 - uint8_t external_antenna:1; // false = internal antenna, true = external antenna - uint8_t spare2:1; - uint8_t spare3; + uint8_t external_antenna:1; // false = internal antenna, true = external antenna + uint8_t sport_out:1; + uint8_t spare2; } pxx); + NOBACKUP(struct { + uint8_t spare1:6; + uint8_t noninverted:1; + uint8_t spare2:1; + int8_t refreshRate; // definition as framelength for ppm (* 5 + 225 = time in 1/10 ms) + } sbus); }; // Helper functions to set both of the rfProto protocol at the same time @@ -756,7 +761,9 @@ #define MODEL_GVARS_DATA GVarData gvars[MAX_GVARS]; #endif -#if defined(TELEMETRY_MAVLINK) +#if defined(CPUARM) + #define TELEMETRY_DATA NOBACKUP(FrSkyTelemetryData frsky); NOBACKUP(RssiAlarmData rssiAlarms); +#elif defined(TELEMETRY_MAVLINK) #define TELEMETRY_DATA MavlinkTelemetryData mavlink; #elif defined(TELEMETRY_FRSKY) || !defined(PCBSTD) #define TELEMETRY_DATA NOBACKUP(FrSkyTelemetryData frsky); @@ -880,7 +887,7 @@ #define SPLASH_MODE uint8_t splashSpares:3 #elif defined(FSPLASH) #define SPLASH_MODE uint8_t splashMode:3 -#elif defined(PCBTARANIS) +#elif defined(CPUARM) #define SPLASH_MODE int8_t splashMode:3 #else #define SPLASH_MODE uint8_t splashMode:1; uint8_t splashSpare:2 @@ -890,11 +897,14 @@ #define EXTRA_GENERAL_FIELDS_ARM \ NOBACKUP(uint8_t backlightBright); \ NOBACKUP(uint32_t globalTimer); \ - NOBACKUP(uint8_t btBaudrate); \ + NOBACKUP(uint8_t bluetoothBaudrate:4); \ + NOBACKUP(uint8_t bluetoothMode:4); \ NOBACKUP(uint8_t countryCode); \ NOBACKUP(uint8_t imperial:1); \ NOBACKUP(uint8_t jitterFilter:1); /* 0 - active */\ - NOBACKUP(uint8_t spareExtraArm:6); \ + NOBACKUP(uint8_t disableRssiPoweroffAlarm:1); \ + NOBACKUP(uint8_t USBMode:2); \ + NOBACKUP(uint8_t spareExtraArm:3); \ NOBACKUP(char ttsLanguage[2]); \ NOBACKUP(int8_t beepVolume:4); \ NOBACKUP(int8_t wavVolume:4); \ @@ -916,7 +926,7 @@ NOBACKUP(char switchNames[NUM_SWITCHES][LEN_SWITCH_NAME]); \ NOBACKUP(char anaNames[NUM_STICKS+NUM_POTS+NUM_SLIDERS+NUM_DUMMY_ANAS][LEN_ANA_NAME]); \ NOBACKUP(char currModelFilename[LEN_MODEL_FILENAME+1]); \ - NOBACKUP(uint8_t bluetoothEnable:1); \ + NOBACKUP(uint8_t spare:1); \ NOBACKUP(uint8_t blOffBright:7); \ NOBACKUP(char bluetoothName[LEN_BLUETOOTH_NAME]); #elif defined(PCBFLAMENCO) @@ -931,7 +941,7 @@ #elif defined(PCBTARANIS) #if defined(PCBX9E) || defined(PCBX7) #define BLUETOOTH_FIELDS \ - uint8_t bluetoothEnable; \ + uint8_t spare; \ char bluetoothName[LEN_BLUETOOTH_NAME]; #else #define BLUETOOTH_FIELDS @@ -1005,7 +1015,8 @@ NOBACKUP(int8_t timezone:5); NOBACKUP(uint8_t adjustRTC:1); NOBACKUP(uint8_t inactivityTimer); - NOBACKUP(uint8_t mavbaud:3); + AVR_FIELD(uint8_t mavbaud:3) + ARM_FIELD(uint8_t telemetryBaudrate:3) SPLASH_MODE; /* 3bits */ NOBACKUP(int8_t hapticMode:2); // -2=quiet, -1=only alarms, 0=no keys, 1=all AVR_FIELD(uint8_t blOffBright:4) @@ -1066,8 +1077,6 @@ #endif /* Difference between Taranis/Horus is LEN_EXPOMIX_NAME */ - /* Sky9x does not have virtualinputs */ - /* LEN_FUNCTION_NAME is the difference in CustomFunctionData */ #if defined(PCBX7) @@ -1082,7 +1091,7 @@ CHKSIZE(FrSkyBarData, 6); CHKSIZE(FrSkyLineData, 4); CHKTYPE(union FrSkyScreenData, 24); - CHKSIZE(FrSkyTelemetryData, 106); + CHKSIZE(FrSkyTelemetryData, 104); CHKSIZE(ModelHeader, 12); CHKSIZE(CurveData, 4); @@ -1101,7 +1110,7 @@ CHKSIZE(FrSkyBarData, 6); CHKSIZE(FrSkyLineData, 6); CHKTYPE(union FrSkyScreenData, 24); - CHKSIZE(FrSkyTelemetryData, 106); + CHKSIZE(FrSkyTelemetryData, 104); CHKSIZE(ModelHeader, 24); CHKSIZE(CurveData, 4); #if defined(PCBX9E) @@ -1123,7 +1132,7 @@ CHKSIZE(TimerData, 16); CHKSIZE(SwashRingData, 8); - CHKSIZE(FrSkyTelemetryData, 7); + CHKSIZE(FrSkyTelemetryData, 5); CHKSIZE(ModelHeader, 27); CHKSIZE(CurveData, 4); CHKSIZE(RadioData, 847); @@ -1140,7 +1149,7 @@ CHKSIZE(SwashRingData, 8); CHKSIZE(FrSkyBarData, 5); CHKSIZE(FrSkyLineData, 2); - CHKSIZE(FrSkyTelemetryData, 90); + CHKSIZE(FrSkyTelemetryData, 88); CHKSIZE(ModelHeader, 12); CHKTYPE(CurveData, 4); CHKSIZE(RadioData, 727); @@ -1184,9 +1193,6 @@ #if defined(CPUARM) CHKSIZE(LogicalSwitchData, 9); -#if !defined(COLORLCD) - CHKSIZE(FrSkyChannelData, 7); -#endif CHKSIZE(TelemetrySensor, 13); CHKSIZE(ModuleData,70); #else @@ -1199,7 +1205,11 @@ CHKSIZE(GVarData, 7); #endif +#if defined(CPUARM) + CHKSIZE(RssiAlarmData, 2); +#else CHKSIZE(FrSkyRSSIAlarm, 1); +#endif CHKSIZE(TrainerData, 16); #undef CHKSIZE diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/debug.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/debug.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/debug.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/debug.cpp 2017-11-10 17:23:25.000000000 +0000 @@ -235,12 +235,12 @@ "Pulses int." // debugTimerIntPulses, ,"Pulses dur." // debugTimerIntPulsesDuration, ,"10ms dur. " // debugTimerPer10ms, + ,"10ms period" // debugTimerPer10msPeriod, ,"Rotary enc." // debugTimerRotEnc, ,"Haptic " // debugTimerHaptic, ,"Mixer calc " // debugTimerMixer, ,"Tel. wakeup" // debugTimerTelemetryWakeup, ,"perMain dur" // debugTimerPerMain, - ," period " // debugTimerPerMainPeriod, ," perMain s1" // debugTimerPerMain1, ," guiMain " // debugTimerGuiMain, ," LUA bg " // debugTimerLuaBg, diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/debug.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/debug.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/debug.h 2017-04-27 08:57:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/debug.h 2017-11-10 17:23:25.000000000 +0000 @@ -34,6 +34,8 @@ extern "C" { #endif +uint8_t serial2TracesEnabled(); + #if defined(SIMU) typedef void (*traceCallbackFunc)(const char * text); extern traceCallbackFunc traceCallback; @@ -41,14 +43,10 @@ #elif defined(SEMIHOSTING) #include #define debugPrintf(...) printf(__VA_ARGS__) -#elif defined(DEBUG) && defined(CLI) && defined(USB_SERIAL) - #define debugPrintf(...) do { if (cliTracesEnabled) serialPrintf(__VA_ARGS__); } while(0) #elif defined(DEBUG) && defined(CLI) - uint8_t serial2TracesEnabled(); - #define debugPrintf(...) do { if (serial2TracesEnabled() && cliTracesEnabled) serialPrintf(__VA_ARGS__); } while(0) -#elif defined(DEBUG) && defined(CPUARM) - uint8_t serial2TracesEnabled(); - #define debugPrintf(...) do { if (serial2TracesEnabled()) serialPrintf(__VA_ARGS__); } while(0) + #define debugPrintf(...) do { if (cliTracesEnabled) serialPrintf(__VA_ARGS__); } while(0) +#elif defined(DEBUG) && defined(CPUARM) && defined(SERIAL2) + #define debugPrintf(...) do { serialPrintf(__VA_ARGS__); } while(0) #else #define debugPrintf(...) #endif @@ -371,12 +369,12 @@ debugTimerIntPulses, debugTimerIntPulsesDuration, debugTimerPer10ms, + debugTimerPer10msPeriod, debugTimerRotEnc, debugTimerHaptic, debugTimerMixer, debugTimerTelemetryWakeup, debugTimerPerMain, - debugTimerPerMainPeriod, debugTimerPerMain1, debugTimerGuiMain, debugTimerLuaBg, Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/src/fonts/sqt5/font_03x05.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/src/fonts/sqt5/font_03x05.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/src/fonts/sqt5/font_04x06_extra.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/src/fonts/sqt5/font_04x06_extra.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/src/fonts/sqt5/font_05x07_extra.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/src/fonts/sqt5/font_05x07_extra.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/src/fonts/sqt5/font_10x14_extra.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/src/fonts/sqt5/font_10x14_extra.png differ Binary files /tmp/tmpu9V3UX/7X1RGXpOdN/opentx-companion22-2.2.0~ppa02~xenial/radio/src/fonts/sqt5/font_22x38_num.png and /tmp/tmpu9V3UX/sx5Z8K3XW3/opentx-companion22-2.2.1~ppa01~xenial/radio/src/fonts/sqt5/font_22x38_num.png differ diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/functions.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/functions.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/functions.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/functions.cpp 2017-11-15 20:54:40.000000000 +0000 @@ -211,7 +211,7 @@ #endif #if defined(CPUARM) -void playCustomFunctionFile(const CustomFunctionData *sd, uint8_t id) +void playCustomFunctionFile(const CustomFunctionData * sd, uint8_t id) { if (sd->play.name[0] != '\0') { char filename[sizeof(SOUNDS_PATH)+sizeof(sd->play.name)+sizeof(SOUNDS_EXT)] = SOUNDS_PATH "/"; @@ -330,46 +330,46 @@ break; case FUNC_RESET: - if (!(functionsContext.activeSwitches & switch_mask)) { - switch (CFN_PARAM(cfn)) { - case FUNC_RESET_TIMER1: - case FUNC_RESET_TIMER2: -#if defined(CPUARM) - case FUNC_RESET_TIMER3: -#endif - timerReset(CFN_PARAM(cfn)); - break; - case FUNC_RESET_FLIGHT: + switch (CFN_PARAM(cfn)) { + case FUNC_RESET_TIMER1: + case FUNC_RESET_TIMER2: +#if defined(CPUARM) + case FUNC_RESET_TIMER3: +#endif + timerReset(CFN_PARAM(cfn)); + break; + case FUNC_RESET_FLIGHT: + if (!(functionsContext.activeSwitches & switch_mask)) { #if defined(CPUARM) mainRequestFlags |= (1 << REQUEST_FLIGHT_RESET); // on systems with threads flightReset() must not be called from the mixers thread! #else flightReset(); #endif // defined(CPUARM) - break; + } + break; #if defined(TELEMETRY_FRSKY) - case FUNC_RESET_TELEMETRY: - telemetryReset(); - break; + case FUNC_RESET_TELEMETRY: + telemetryReset(); + break; #endif #if ROTARY_ENCODERS > 0 - case FUNC_RESET_ROTENC1: + case FUNC_RESET_ROTENC1: #if ROTARY_ENCODERS > 1 - case FUNC_RESET_ROTENC2: + case FUNC_RESET_ROTENC2: #endif - rotencValue[CFN_PARAM(cfn)-FUNC_RESET_ROTENC1] = 0; - break; + rotencValue[CFN_PARAM(cfn)-FUNC_RESET_ROTENC1] = 0; + break; #endif - } + } #if defined(CPUARM) - if (CFN_PARAM(cfn)>=FUNC_RESET_PARAM_FIRST_TELEM) { - uint8_t item = CFN_PARAM(cfn)-FUNC_RESET_PARAM_FIRST_TELEM; - if (item < MAX_TELEMETRY_SENSORS) { - telemetryItems[item].clear(); - } + if (CFN_PARAM(cfn)>=FUNC_RESET_PARAM_FIRST_TELEM) { + uint8_t item = CFN_PARAM(cfn)-FUNC_RESET_PARAM_FIRST_TELEM; + if (item < MAX_TELEMETRY_SENSORS) { + telemetryItems[item].clear(); } -#endif } +#endif break; #if defined(CPUARM) @@ -416,7 +416,7 @@ else if (CFN_GVAR_MODE(cfn) == FUNC_ADJUST_GVAR_INCDEC) { if (!(functionsContext.activeSwitches & switch_mask)) { #if defined(CPUARM) - SET_GVAR(CFN_GVAR_INDEX(cfn), limit(CFN_GVAR_CST_MIN+g_model.gvars[CFN_GVAR_INDEX(cfn)].min, GVAR_VALUE(CFN_GVAR_INDEX(cfn), getGVarFlightMode(mixerCurrentFlightMode, CFN_GVAR_INDEX(cfn))) + CFN_PARAM(cfn), CFN_GVAR_CST_MAX-g_model.gvars[CFN_GVAR_INDEX(cfn)].max), mixerCurrentFlightMode); + SET_GVAR(CFN_GVAR_INDEX(cfn), limit(MODEL_GVAR_MIN(CFN_GVAR_INDEX(cfn)), GVAR_VALUE(CFN_GVAR_INDEX(cfn), getGVarFlightMode(mixerCurrentFlightMode, CFN_GVAR_INDEX(cfn))) + CFN_PARAM(cfn), MODEL_GVAR_MAX(CFN_GVAR_INDEX(cfn))), mixerCurrentFlightMode); #else SET_GVAR(CFN_GVAR_INDEX(cfn), GVAR_VALUE(CFN_GVAR_INDEX(cfn), getGVarFlightMode(mixerCurrentFlightMode, CFN_GVAR_INDEX(cfn))) + (CFN_PARAM(cfn) ? +1 : -1), mixerCurrentFlightMode); #endif @@ -429,12 +429,20 @@ else if (CFN_PARAM(cfn) >= MIXSRC_REa && CFN_PARAM(cfn) < MIXSRC_TrimRud) { int8_t scroll = rePreviousValues[CFN_PARAM(cfn)-MIXSRC_REa] - (rotencValue[CFN_PARAM(cfn)-MIXSRC_REa] / ROTARY_ENCODER_GRANULARITY); if (scroll) { +#if defined(CPUARM) + SET_GVAR(CFN_GVAR_INDEX(cfn), limit(MODEL_GVAR_MIN(CFN_GVAR_INDEX(cfn)), GVAR_VALUE(CFN_GVAR_INDEX(cfn), getGVarFlightMode(mixerCurrentFlightMode, CFN_GVAR_INDEX(cfn))) + scroll, MODEL_GVAR_MAX(CFN_GVAR_INDEX(cfn))), mixerCurrentFlightMode); +#else SET_GVAR(CFN_GVAR_INDEX(cfn), GVAR_VALUE(CFN_GVAR_INDEX(cfn), getGVarFlightMode(mixerCurrentFlightMode, CFN_GVAR_INDEX(cfn))) + scroll, mixerCurrentFlightMode); +#endif } } #endif else { +#if defined(CPUARM) + SET_GVAR(CFN_GVAR_INDEX(cfn), limit(MODEL_GVAR_MIN(CFN_GVAR_INDEX(cfn)), calcRESXto100(getValue(CFN_PARAM(cfn))), MODEL_GVAR_MAX(CFN_GVAR_INDEX(cfn))), mixerCurrentFlightMode); +#else SET_GVAR(CFN_GVAR_INDEX(cfn), calcRESXto100(getValue(CFN_PARAM(cfn))), mixerCurrentFlightMode); +#endif } break; #endif diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/128x64/bmp.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/128x64/bmp.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/128x64/bmp.cpp 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/128x64/bmp.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -0,0 +1,159 @@ +/* + * Copyright (C) OpenTX + * + * Based on code named + * th9x - http://code.google.com/p/th9x + * er9x - http://code.google.com/p/er9x + * gruvin9x - http://code.google.com/p/gruvin9x + * + * License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + * + * 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. + */ + +#include "opentx.h" + +uint8_t * lcdLoadBitmap(uint8_t * bmp, const char * filename, uint8_t width, uint8_t height) +{ + FIL bmpFile; + UINT read; + uint8_t bmpBuf[LCD_W]; /* maximum with LCD_W */ + uint8_t * buf = &bmpBuf[0]; + + if (width > LCD_W) { + return NULL; + } + + FRESULT result = f_open(&bmpFile, filename, FA_OPEN_EXISTING | FA_READ); + if (result != FR_OK) { + return NULL; + } + + if (f_size(&bmpFile) < 14) { + f_close(&bmpFile); + return NULL; + } + + result = f_read(&bmpFile, buf, 14, &read); + if (result != FR_OK || read != 14) { + f_close(&bmpFile); + return NULL; + } + + if (buf[0] != 'B' || buf[1] != 'M') { + f_close(&bmpFile); + return NULL; + } + + uint32_t fsize = *((uint32_t *)&buf[2]); + uint32_t hsize = *((uint32_t *)&buf[10]); /* header size */ + + uint32_t len = limit((uint32_t)4, (uint32_t)(hsize-14), (uint32_t)32); + result = f_read(&bmpFile, buf, len, &read); + if (result != FR_OK || read != len) { + f_close(&bmpFile); + return NULL; + } + + uint32_t ihsize = *((uint32_t *)&buf[0]); /* more header size */ + + /* invalid header size */ + if (ihsize + 14 > hsize) { + f_close(&bmpFile); + return NULL; + } + + /* sometimes file size is set to some headers size, set a real size in that case */ + if (fsize == 14 || fsize == ihsize + 14) { + fsize = f_size(&bmpFile) - 2; + } + + /* declared file size less than header size */ + if (fsize <= hsize) { + f_close(&bmpFile); + return NULL; + } + + uint32_t w, h; + + switch (ihsize){ + case 40: // windib + case 56: // windib v3 + case 64: // OS/2 v2 + case 108: // windib v4 + case 124: // windib v5 + w = *((uint32_t *)&buf[4]); + h = *((uint32_t *)&buf[8]); + buf += 12; + break; + case 12: // OS/2 v1 + w = *((uint16_t *)&buf[4]); + h = *((uint16_t *)&buf[6]); + buf += 8; + break; + default: + f_close(&bmpFile); + return NULL; + } + + if (*((uint16_t *)&buf[0]) != 1) { /* planes */ + f_close(&bmpFile); + return NULL; + } + + if (w > width || h > height) { + f_close(&bmpFile); + return NULL; + } + + uint16_t depth = *((uint16_t *)&buf[2]); + + buf = &bmpBuf[0]; + + if (f_lseek(&bmpFile, hsize) != FR_OK) { + f_close(&bmpFile); + return NULL; + } + + uint8_t * dest = bmp; + + *dest++ = w; + *dest++ = h; + + memset(dest, 0, BITMAP_BUFFER_SIZE(w, h) - 2); + + uint8_t rowSize = (w + 7) / 8; + + switch (depth) { + case 1: + for (int8_t i=h-1; i>=0; i--) { + result = f_read(&bmpFile, buf, rowSize, &read); + if (result != FR_OK || read != rowSize) { + f_close(&bmpFile); + return NULL; + } + + for (uint8_t j=0; j> 1) + ((pat & 1) << 7); } #else - for (scoord_t i=y; i= LCD_LINES) return; + + uint8_t *p = &displayBuf[line * LCD_W]; for (coord_t x=0; x= i) { + if (4 - quarter >= i) { lcdDrawFilledRect(LCD_W / 2 - 28 + 10 * i, LCD_H / 2 - 3, 6, 6, SOLID, 0); } } + if (message) { + lcdDrawText((LCD_W - getTextWidth(message)) / 2, LCD_H-2*FH, message); + } lcdRefresh(); } #endif diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/128x64/lcd.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/128x64/lcd.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/128x64/lcd.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/128x64/lcd.h 2017-10-31 16:16:43.000000000 +0000 @@ -44,6 +44,8 @@ #define LCD_LINES (LCD_H/FH) #define LCD_COLS (LCD_W/FW) +#define BITMAP_BUFFER_SIZE(w, h) (2 + (w) * (((h)+7)/8)) + /* lcd common flags */ #define BLINK 0x01 @@ -94,7 +96,8 @@ #define NO_UNIT 0x40 #if defined(CPUARM) - #define FONTSIZE(x) ((x) & 0x0700) + #define FONTSIZE_MASK 0x0700 + #define FONTSIZE(x) ((x) & FONTSIZE_MASK) #define TINSIZE 0x0100 #define SMLSIZE 0x0200 #define MIDSIZE 0x0300 @@ -260,7 +263,13 @@ #endif void lcdClear(void); -void lcd_img(coord_t x, coord_t y, const pm_uchar * img, uint8_t idx, LcdFlags att=0); +void lcdDraw1bitBitmap(coord_t x, coord_t y, const pm_uchar * img, uint8_t idx, LcdFlags att=0); +inline void lcdDrawBitmap(coord_t x, coord_t y, const uint8_t * bitmap) +{ + lcdDraw1bitBitmap(x, y, bitmap, 0); +} + +uint8_t * lcdLoadBitmap(uint8_t * dest, const char * filename, uint8_t width, uint8_t height); #if defined(BOOT) #define BLINK_ON_PHASE (0) @@ -281,6 +290,10 @@ const char * writeScreenshot(); -void drawShutdownAnimation(uint32_t index); +void drawShutdownAnimation(uint32_t index, const char * message); + +#if defined(CPUARM) +uint8_t getTextWidth(const char * s, uint8_t len=0, LcdFlags flags=0); +#endif #endif // _LCD_H_ diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/128x64/menus.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/128x64/menus.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/128x64/menus.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/128x64/menus.h 2017-10-31 16:16:43.000000000 +0000 @@ -171,10 +171,7 @@ void menuStatisticsView(event_t event); void menuStatisticsDebug(event_t event); +void menuStatisticsDebug2(event_t event); void menuAboutView(event_t event); -#if defined(DEBUG_TRACE_BUFFER) -void menuTraceBuffer(event_t event); -#endif - #endif // _MENUS_H_ diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/128x64/model_display.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/128x64/model_display.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/128x64/model_display.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/128x64/model_display.cpp 2017-11-15 20:54:40.000000000 +0000 @@ -50,7 +50,7 @@ #else #define DISPLAY_COL2 (8*FW) #endif -#define DISPLAY_COL3 (18*FW+2) +#define DISPLAY_COL3 (17*FW+2) #if defined(LUA) #define SCREEN_TYPE_ROWS 1 @@ -105,7 +105,7 @@ MENU(STR_MENU_DISPLAY, menuTabModel, MENU_MODEL_DISPLAY, HEADER_LINE + ITEM_DISPLAY_MAX, { HEADER_LINE_COLUMNS TELEMETRY_SCREEN_ROWS(0), TELEMETRY_SCREEN_ROWS(1), TELEMETRY_SCREEN_ROWS(2), TELEMETRY_SCREEN_ROWS(3) }); int8_t sub = menuVerticalPosition - HEADER_LINE; - + for (uint8_t i=0; imin = 0; @@ -196,9 +195,11 @@ } else if (result == STR_COPY_STICKS_TO_OFS) { copySticksToOffset(s_currIdx); + storageDirty(EE_MODEL); } else if (result == STR_COPY_TRIMS_TO_OFS) { copyTrimsToOffset(s_currIdx); + storageDirty(EE_MODEL); } else if (result == STR_EDIT) { pushMenu(menuModelLimitsOne); @@ -221,7 +222,7 @@ uint8_t k = i+menuVerticalOffset; LcdFlags attr = (sub==MAX_OUTPUT_CHANNELS) ? INVERS : 0; - if (sub==k && event==EVT_KEY_FIRST(KEY_ENTER) && !READ_ONLY()) { + if (sub==k && event==EVT_KEY_FIRST(KEY_ENTER) && !READ_ONLY() && (k != MAX_OUTPUT_CHANNELS) ) { killEvents(event); POPUP_MENU_ADD_ITEM(STR_EDIT); POPUP_MENU_ADD_ITEM(STR_RESET); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/128x64/model_setup.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/128x64/model_setup.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/128x64/model_setup.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/128x64/model_setup.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -71,6 +71,7 @@ #if defined(MULTIMODULE) ITEM_MODEL_EXTERNAL_MODULE_SUBTYPE, ITEM_MODEL_EXTERNAL_MODULE_STATUS, + ITEM_MODEL_EXTERNAL_MODULE_SYNCSTATUS, #endif ITEM_MODEL_EXTERNAL_MODULE_CHANNELS, ITEM_MODEL_EXTERNAL_MODULE_BIND, @@ -78,10 +79,11 @@ ITEM_MODEL_EXTERNAL_MODULE_OUTPUT_TYPE, #endif ITEM_MODEL_EXTERNAL_MODULE_FAILSAFE, + ITEM_MODEL_EXTERNAL_MODULE_OPTIONS, #if defined(MULTIMODULE) ITEM_MODEL_EXTERNAL_MODULE_AUTOBIND, - ITEM_MODEL_EXTERNAL_MODULE_LOWPOWER, #endif + ITEM_MODEL_EXTERNAL_MODULE_POWER, #if defined(PCBSKY9X) && !defined(REVA) ITEM_MODEL_EXTRA_MODULE_LABEL, ITEM_MODEL_EXTRA_MODULE_CHANNELS, @@ -94,8 +96,11 @@ #if defined(PCBX7) ITEM_MODEL_TRAINER_LABEL, ITEM_MODEL_TRAINER_MODE, +#if defined(BLUETOOTH) + ITEM_MODEL_TRAINER_BLUETOOTH, +#endif ITEM_MODEL_TRAINER_CHANNELS, - ITEM_MODEL_TRAINER_SETTINGS, + ITEM_MODEL_TRAINER_PARAMS, #endif ITEM_MODEL_SETUP_MAX }; @@ -126,16 +131,10 @@ #else #define INTERNAL_MODULE_MODE_ROWS (IS_MODULE_XJT(INTERNAL_MODULE) ? (uint8_t)1 : (uint8_t)0) // Module type + RF protocols #endif -#if defined(TARANIS_INTERNAL_PPM) - #define IF_INTERNAL_MODULE_ON(x) (g_model.moduleData[INTERNAL_MODULE].type == MODULE_TYPE_NONE ? HIDDEN_ROW : (uint8_t)(x)) -#else - #define IF_INTERNAL_MODULE_ON(x) (g_model.moduleData[INTERNAL_MODULE].rfProtocol == RF_PROTO_OFF ? HIDDEN_ROW : (uint8_t)(x)) -#endif - - #define IF_EXTERNAL_MODULE_ON(x) (g_model.moduleData[EXTERNAL_MODULE].type == MODULE_TYPE_NONE ? HIDDEN_ROW : (uint8_t)(x)) - #define IF_EXTERNAL_MODULE_XJT(x) (IS_MODULE_XJT(EXTERNAL_MODULE) ? (uint8_t)(x) : HIDDEN_ROW) + #define IF_INTERNAL_MODULE_ON(x) (IS_INTERNAL_MODULE_ENABLED()? (uint8_t)(x) : HIDDEN_ROW ) + #define IF_EXTERNAL_MODULE_ON(x) (IS_EXTERNAL_MODULE_ENABLED()? (uint8_t)(x) : HIDDEN_ROW) #define INTERNAL_MODULE_CHANNELS_ROWS IF_INTERNAL_MODULE_ON(1) - #define EXTERNAL_MODULE_BIND_ROWS() (IS_MODULE_XJT(EXTERNAL_MODULE) && IS_D8_RX(EXTERNAL_MODULE)) ? (uint8_t)1 : (IS_MODULE_PPM(EXTERNAL_MODULE) || IS_MODULE_XJT(EXTERNAL_MODULE) || IS_MODULE_DSM2(EXTERNAL_MODULE) || IS_MODULE_MULTIMODULE(EXTERNAL_MODULE)) ? (uint8_t)2 : HIDDEN_ROW + #define EXTERNAL_MODULE_BIND_ROWS() ((IS_MODULE_XJT(EXTERNAL_MODULE) && IS_D8_RX(EXTERNAL_MODULE)) || IS_MODULE_SBUS(EXTERNAL_MODULE)) ? (uint8_t)1 : (IS_MODULE_PPM(EXTERNAL_MODULE) || IS_MODULE_PXX(EXTERNAL_MODULE) || IS_MODULE_DSM2(EXTERNAL_MODULE) || IS_MODULE_MULTIMODULE(EXTERNAL_MODULE)) ? (uint8_t)2 : HIDDEN_ROW #if defined(PCBSKY9X) && defined(REVX) #define OUTPUT_TYPE_ROWS() (IS_MODULE_PPM(EXTERNAL_MODULE) ? (uint8_t)0 : HIDDEN_ROW) , @@ -144,7 +143,7 @@ #endif #define PORT_CHANNELS_ROWS(x) (x==EXTERNAL_MODULE ? EXTERNAL_MODULE_CHANNELS_ROWS : 0) - #define EXTERNAL_MODULE_MODE_ROWS (IS_MODULE_XJT(EXTERNAL_MODULE) || IS_MODULE_DSM2(EXTERNAL_MODULE) || IS_MODULE_MULTIMODULE(EXTERNAL_MODULE)) ? (uint8_t)1 : (uint8_t)0 + #define EXTERNAL_MODULE_MODE_ROWS (IS_MODULE_PXX(EXTERNAL_MODULE) || IS_MODULE_DSM2(EXTERNAL_MODULE) || IS_MODULE_MULTIMODULE(EXTERNAL_MODULE)) ? (uint8_t)1 : (uint8_t)0 #define CURSOR_ON_CELL (true) #define MODEL_SETUP_MAX_LINES (HEADER_LINE+ITEM_MODEL_SETUP_MAX) @@ -157,10 +156,18 @@ #endif #if defined(PCBX7) - #define TRAINER_CHANNELS_ROWS() IF_TRAINER_ON(1) - #define TRAINER_MODULE_ROWS LABEL(Trainer), 0, TRAINER_CHANNELS_ROWS(), IF_TRAINER_ON(2) +#if defined(BLUETOOTH) + #define TRAINER_BLUETOOTH_M_ROW ((bluetoothDistantAddr[0] == '\0' || bluetoothState == BLUETOOTH_STATE_CONNECTED) ? (uint8_t)0 : (uint8_t)1) + #define TRAINER_BLUETOOTH_S_ROW (bluetoothDistantAddr[0] == '\0' ? HIDDEN_ROW : LABEL()) + #define TRAINER_BLUETOOTH_ROW (g_model.trainerMode == TRAINER_MODE_MASTER_BLUETOOTH ? TRAINER_BLUETOOTH_M_ROW : (g_model.trainerMode == TRAINER_MODE_SLAVE_BLUETOOTH ? TRAINER_BLUETOOTH_S_ROW : HIDDEN_ROW)), #else - #define TRAINER_MODULE_ROWS + #define TRAINER_BLUETOOTH_ROW +#endif +#define TRAINER_CHANNELS_ROW (IS_SLAVE_TRAINER() ? (uint8_t)1 : HIDDEN_ROW) +#define TRAINER_PARAMS_ROW (IS_SLAVE_TRAINER() ? (uint8_t)2 : HIDDEN_ROW) +#define TRAINER_ROWS LABEL(Trainer), 0, TRAINER_BLUETOOTH_ROW TRAINER_CHANNELS_ROW, TRAINER_PARAMS_ROW +#else + #define TRAINER_ROWS #endif #elif defined(CPUM64) @@ -171,33 +178,56 @@ #define MODEL_SETUP_MAX_LINES ((IS_PPM_PROTOCOL(protocol)||IS_DSM2_PROTOCOL(protocol)||IS_PXX_PROTOCOL(protocol)) ? HEADER_LINE+ITEM_MODEL_SETUP_MAX : HEADER_LINE+ITEM_MODEL_SETUP_MAX-1) #endif -#if defined(BINDING_OPTIONS) +#if defined(PCBTARANIS) void onBindMenu(const char * result) { - if (result == STR_BINDING_1_8_TELEM_ON) { - g_model.moduleData[INTERNAL_MODULE].pxx.receiver_telem_off = false; - g_model.moduleData[INTERNAL_MODULE].pxx.receiver_channel_9_16 = false; + uint8_t moduleIdx = CURRENT_MODULE_EDITED(menuVerticalPosition); + + if (result == STR_BINDING_25MW_CH1_8_TELEM_OFF) { + g_model.moduleData[moduleIdx].pxx.power = R9M_LBT_POWER_25; + g_model.moduleData[moduleIdx].pxx.receiver_telem_off = true; + g_model.moduleData[moduleIdx].pxx.receiver_channel_9_16 = false; + } + else if (result == STR_BINDING_25MW_CH1_8_TELEM_ON) { + g_model.moduleData[moduleIdx].pxx.power = R9M_LBT_POWER_25; + g_model.moduleData[moduleIdx].pxx.receiver_telem_off = false; + g_model.moduleData[moduleIdx].pxx.receiver_channel_9_16 = false; + } + else if (result == STR_BINDING_500MW_CH1_8_TELEM_OFF) { + g_model.moduleData[moduleIdx].pxx.power = R9M_LBT_POWER_500; + g_model.moduleData[moduleIdx].pxx.receiver_telem_off = true; + g_model.moduleData[moduleIdx].pxx.receiver_channel_9_16 = false; + } + else if (result == STR_BINDING_500MW_CH9_16_TELEM_OFF) { + g_model.moduleData[moduleIdx].pxx.power = R9M_LBT_POWER_500; + g_model.moduleData[moduleIdx].pxx.receiver_telem_off = true; + g_model.moduleData[moduleIdx].pxx.receiver_channel_9_16 = true; + } + else if (result == STR_BINDING_1_8_TELEM_ON) { + g_model.moduleData[moduleIdx].pxx.receiver_telem_off = false; + g_model.moduleData[moduleIdx].pxx.receiver_channel_9_16 = false; } else if (result == STR_BINDING_1_8_TELEM_OFF) { - g_model.moduleData[INTERNAL_MODULE].pxx.receiver_telem_off = true; - g_model.moduleData[INTERNAL_MODULE].pxx.receiver_channel_9_16 = false; + g_model.moduleData[moduleIdx].pxx.receiver_telem_off = true; + g_model.moduleData[moduleIdx].pxx.receiver_channel_9_16 = false; } else if (result == STR_BINDING_9_16_TELEM_ON) { - g_model.moduleData[INTERNAL_MODULE].pxx.receiver_telem_off = false; - g_model.moduleData[INTERNAL_MODULE].pxx.receiver_channel_9_16 = true; + g_model.moduleData[moduleIdx].pxx.receiver_telem_off = false; + g_model.moduleData[moduleIdx].pxx.receiver_channel_9_16 = true; } else if (result == STR_BINDING_9_16_TELEM_OFF) { - g_model.moduleData[INTERNAL_MODULE].pxx.receiver_telem_off = true; - g_model.moduleData[INTERNAL_MODULE].pxx.receiver_channel_9_16 = true; + g_model.moduleData[moduleIdx].pxx.receiver_telem_off = true; + g_model.moduleData[moduleIdx].pxx.receiver_channel_9_16 = true; } else { return; } - moduleFlag[INTERNAL_MODULE] = MODULE_BIND; + moduleFlag[moduleIdx] = MODULE_BIND; } #endif + void menuModelSetup(event_t event) { #if defined(PCBX7) @@ -210,27 +240,31 @@ LABEL(ExternalModule), EXTERNAL_MODULE_MODE_ROWS, MULTIMODULE_SUBTYPE_ROWS(EXTERNAL_MODULE) - MULTIMODULE_STATUS_ROW + MULTIMODULE_STATUS_ROWS EXTERNAL_MODULE_CHANNELS_ROWS, EXTERNAL_MODULE_BIND_ROWS(), OUTPUT_TYPE_ROWS() FAILSAFE_ROWS(EXTERNAL_MODULE), + EXTERNAL_MODULE_OPTION_ROW, MULTIMODULE_MODULE_ROWS + EXTERNAL_MODULE_POWER_ROW, EXTRA_MODULE_ROWS - TRAINER_MODULE_ROWS }); + TRAINER_ROWS }); #elif defined(CPUARM) MENU_TAB({ HEADER_LINE_COLUMNS 0, TIMER_ROWS, TIMER_ROWS, TIMER_ROWS, 0, 1, 0, 0, 0, 0, 0, CASE_CPUARM(LABEL(PreflightCheck)) CASE_CPUARM(0) 0, NUM_SWITCHES-1, NUM_STICKS+NUM_POTS+NUM_SLIDERS+NUM_ROTARY_ENCODERS-1, 0, LABEL(ExternalModule), EXTERNAL_MODULE_MODE_ROWS, MULTIMODULE_SUBTYPE_ROWS(EXTERNAL_MODULE) - MULTIMODULE_STATUS_ROW + MULTIMODULE_STATUS_ROWS EXTERNAL_MODULE_CHANNELS_ROWS, EXTERNAL_MODULE_BIND_ROWS(), OUTPUT_TYPE_ROWS() FAILSAFE_ROWS(EXTERNAL_MODULE), + EXTERNAL_MODULE_OPTION_ROW, MULTIMODULE_MODULE_ROWS + EXTERNAL_MODULE_POWER_ROW, EXTRA_MODULE_ROWS - TRAINER_MODULE_ROWS }); + TRAINER_ROWS }); #elif defined(CPUM64) uint8_t protocol = g_model.protocol; MENU_TAB({ HEADER_LINE_COLUMNS 0, 2, CASE_PERSISTENT_TIMERS(0) 0, 0, 2, CASE_PERSISTENT_TIMERS(0) 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, NUM_STICKS+NUM_POTS+NUM_SLIDERS+NUM_ROTARY_ENCODERS-1, FIELD_PROTOCOL_MAX, 2 }); @@ -544,9 +578,10 @@ int current = 0; for (int i=0; isubTypeString != nullptr) lcdDrawTextAtIndex(MODEL_SETUP_2ND_COLUMN, y, pdef->subTypeString, g_model.moduleData[EXTERNAL_MODULE].subType, attr); } @@ -780,7 +824,7 @@ } } } - break; + break; #endif #if defined(PCBX7) @@ -791,13 +835,70 @@ case ITEM_MODEL_TRAINER_MODE: lcdDrawTextAlignedLeft(y, STR_MODE); lcdDrawTextAtIndex(MODEL_SETUP_2ND_COLUMN, y, STR_VTRAINERMODES, g_model.trainerMode, attr); - if (attr) g_model.trainerMode = checkIncDec(event, g_model.trainerMode, 0, HAS_WIRELESS_TRAINER_HARDWARE() ? TRAINER_MODE_MASTER_BATTERY_COMPARTMENT : TRAINER_MODE_MASTER_CPPM_EXTERNAL_MODULE, EE_MODEL, isTrainerModeAvailable); + if (attr) { + g_model.trainerMode = checkIncDec(event, g_model.trainerMode, 0, TRAINER_MODE_MAX(), EE_MODEL, isTrainerModeAvailable); +#if defined(BLUETOOTH) + if (checkIncDec_Ret) { + bluetoothState = BLUETOOTH_STATE_OFF; + bluetoothDistantAddr[0] = 0; + } +#endif + } + break; +#endif + +#if defined(PCBX7) && defined(BLUETOOTH) + case ITEM_MODEL_TRAINER_BLUETOOTH: + if (g_model.trainerMode == TRAINER_MODE_MASTER_BLUETOOTH) { + if (attr) { + s_editMode = 0; + } + if (bluetoothDistantAddr[0]) { + lcdDrawText(INDENT_WIDTH, y+1, bluetoothDistantAddr, TINSIZE); + if (bluetoothState != BLUETOOTH_STATE_CONNECTED) { + lcdDrawText(MODEL_SETUP_2ND_COLUMN, y, BUTTON("Bind"), menuHorizontalPosition == 0 ? attr : 0); + lcdDrawText(MODEL_SETUP_2ND_COLUMN+5*FW, y, BUTTON("Clear"), menuHorizontalPosition == 1 ? attr : 0); + } + else { + lcdDrawText(MODEL_SETUP_2ND_COLUMN, y, BUTTON("Clear"), attr); + } + if (attr && event == EVT_KEY_FIRST(KEY_ENTER)) { + if (bluetoothState == BLUETOOTH_STATE_CONNECTED || menuHorizontalPosition == 1) { + bluetoothState = BLUETOOTH_STATE_OFF; + bluetoothDistantAddr[0] = 0; + } + else { + bluetoothState = BLUETOOTH_STATE_BIND_REQUESTED; + } + } + } + else { + lcdDrawText(INDENT_WIDTH, y, "---"); + if (bluetoothState < BLUETOOTH_STATE_IDLE) + lcdDrawText(MODEL_SETUP_2ND_COLUMN, y, BUTTON("Init"), attr); + else + lcdDrawText(MODEL_SETUP_2ND_COLUMN, y, BUTTON("Discover"), attr); + if (attr && event == EVT_KEY_FIRST(KEY_ENTER)) { + if (bluetoothState < BLUETOOTH_STATE_IDLE) + bluetoothState = BLUETOOTH_STATE_OFF; + else + bluetoothState = BLUETOOTH_STATE_DISCOVER_REQUESTED; + } + } + } + else { + if (bluetoothDistantAddr[0]) + lcdDrawText(INDENT_WIDTH, y+1, bluetoothDistantAddr, TINSIZE); + else + lcdDrawText(INDENT_WIDTH, y, "---"); + lcdDrawText(MODEL_SETUP_2ND_COLUMN, y, bluetoothState == BLUETOOTH_STATE_CONNECTED ? "Connected" : "!Connected"); + } break; #endif #if defined(PCBX7) - case ITEM_MODEL_INTERNAL_MODULE_CHANNELS: case ITEM_MODEL_TRAINER_CHANNELS: + case ITEM_MODEL_INTERNAL_MODULE_CHANNELS: #endif #if defined(PCBSKY9X) case ITEM_MODEL_EXTRA_MODULE_CHANNELS: @@ -832,7 +933,7 @@ #endif #if defined(PCBX7) - case ITEM_MODEL_TRAINER_SETTINGS: + case ITEM_MODEL_TRAINER_PARAMS: case ITEM_MODEL_INTERNAL_MODULE_BIND: #endif #if defined(PCBSKY9X) @@ -864,6 +965,23 @@ } } } + else if (IS_MODULE_SBUS(moduleIdx)) { + lcdDrawTextAlignedLeft(y, STR_REFRESHRATE); + lcdDrawNumber(MODEL_SETUP_2ND_COLUMN, y, (int16_t)moduleData.ppm.frameLength*5 + 225, (menuHorizontalPosition<=0 ? attr : 0) | PREC1|LEFT); + lcdDrawText(lcdLastRightPos, y, STR_MS); + lcdDrawText(MODEL_SETUP_2ND_COLUMN+5*FW+2, y, moduleData.sbus.noninverted ? "no inv" : "normal", (CURSOR_ON_LINE() || menuHorizontalPosition==1) ? attr : 0); + + if (attr && s_editMode>0) { + switch (menuHorizontalPosition) { + case 0: + CHECK_INCDEC_MODELVAR(event, moduleData.ppm.frameLength, -33, 35); + break; + case 1: + CHECK_INCDEC_MODELVAR_ZERO(event, moduleData.sbus.noninverted, 1); + break; + } + } + } else { horzpos_t l_posHorz = menuHorizontalPosition; coord_t xOffsetBind = MODEL_SETUP_BIND_OFS; @@ -875,7 +993,7 @@ else { lcdDrawTextAlignedLeft(y, STR_RECEIVER_NUM); } - if (IS_MODULE_XJT(moduleIdx) || IS_MODULE_DSM2(moduleIdx) || IS_MODULE_MULTIMODULE(moduleIdx)) { + if (IS_MODULE_PXX(moduleIdx) || IS_MODULE_DSM2(moduleIdx) || IS_MODULE_MULTIMODULE(moduleIdx)) { if (xOffsetBind) lcdDrawNumber(MODEL_SETUP_2ND_COLUMN, y, g_model.header.modelId[moduleIdx], (l_posHorz==0 ? attr : 0) | LEADING0|LEFT, 2); if (attr && l_posHorz==0) { if (editMode>0 || p1valdiff) { @@ -897,26 +1015,40 @@ s_editMode=0; } #endif -#if defined(BINDING_OPTIONS) - if (attr && l_posHorz>0) { - if(s_editMode>0) { +#if defined(PCBTARANIS) + if (attr && l_posHorz > 0) { + if (s_editMode > 0) { if (l_posHorz == 1) { - if (IS_MODULE_XJT(moduleIdx) && g_model.moduleData[moduleIdx].rfProtocol== RF_PROTO_X16 && s_current_protocol[INTERNAL_MODULE] == PROTO_PXX) { - if(event==EVT_KEY_BREAK(KEY_ENTER)) { - POPUP_MENU_ADD_ITEM(STR_BINDING_1_8_TELEM_ON); - POPUP_MENU_ADD_ITEM(STR_BINDING_1_8_TELEM_OFF); - POPUP_MENU_ADD_ITEM(STR_BINDING_9_16_TELEM_ON); - POPUP_MENU_ADD_ITEM(STR_BINDING_9_16_TELEM_OFF); - POPUP_MENU_SELECT_ITEM(g_model.moduleData[INTERNAL_MODULE].pxx.receiver_telem_off + (g_model.moduleData[INTERNAL_MODULE].pxx.receiver_channel_9_16 << 1)); + if (IS_MODULE_R9M(moduleIdx) || (IS_MODULE_XJT(moduleIdx) && g_model.moduleData[moduleIdx].rfProtocol== RF_PROTO_X16)) { + if (event == EVT_KEY_BREAK(KEY_ENTER)) { + uint8_t default_selection; + if (IS_MODULE_R9M_LBT(moduleIdx)) { + POPUP_MENU_ADD_ITEM(STR_BINDING_25MW_CH1_8_TELEM_OFF); + if (!IS_TELEMETRY_INTERNAL_MODULE()) + POPUP_MENU_ADD_ITEM(STR_BINDING_25MW_CH1_8_TELEM_ON); + POPUP_MENU_ADD_ITEM(STR_BINDING_500MW_CH1_8_TELEM_OFF); + POPUP_MENU_ADD_ITEM(STR_BINDING_500MW_CH9_16_TELEM_OFF); + default_selection = 2; + } + else { + if (!(IS_TELEMETRY_INTERNAL_MODULE() && moduleIdx == EXTERNAL_MODULE)) + POPUP_MENU_ADD_ITEM(STR_BINDING_1_8_TELEM_ON); + POPUP_MENU_ADD_ITEM(STR_BINDING_1_8_TELEM_OFF); + if (!(IS_TELEMETRY_INTERNAL_MODULE() && moduleIdx == EXTERNAL_MODULE)) + POPUP_MENU_ADD_ITEM(STR_BINDING_9_16_TELEM_ON); + POPUP_MENU_ADD_ITEM(STR_BINDING_9_16_TELEM_OFF); + default_selection = g_model.moduleData[INTERNAL_MODULE].pxx.receiver_telem_off + (g_model.moduleData[INTERNAL_MODULE].pxx.receiver_channel_9_16 << 1); + } + POPUP_MENU_SELECT_ITEM(default_selection); POPUP_MENU_START(onBindMenu); continue; } - if (moduleFlag[INTERNAL_MODULE] == MODULE_BIND) { + if (moduleFlag[moduleIdx] == MODULE_BIND) { newFlag = MODULE_BIND; } else { if (!popupMenuNoItems) { - s_editMode=0; // this is when popup is exited before a choice is made + s_editMode = 0; // this is when popup is exited before a choice is made } } } @@ -927,20 +1059,24 @@ else if (l_posHorz == 2) { newFlag = MODULE_RANGECHECK; } + } + } #else if (attr && l_posHorz>0 && s_editMode>0) { if (l_posHorz == 1) newFlag = MODULE_BIND; - else if (l_posHorz == 2) { + else if (l_posHorz == 2) newFlag = MODULE_RANGECHECK; -#endif - } } +#endif moduleFlag[moduleIdx] = newFlag; + #if defined(MULTIMODULE) - if (newFlag == MODULE_BIND) + if (newFlag == MODULE_BIND) { multiBindStatus = MULTI_BIND_INITIATED; + } #endif + } } break; @@ -961,45 +1097,43 @@ case ITEM_MODEL_INTERNAL_MODULE_FAILSAFE: #endif #if defined(CPUARM) - case ITEM_MODEL_EXTERNAL_MODULE_FAILSAFE: - { + case ITEM_MODEL_EXTERNAL_MODULE_FAILSAFE: { uint8_t moduleIdx = CURRENT_MODULE_EDITED(k); - ModuleData & moduleData = g_model.moduleData[moduleIdx]; - if (IS_MODULE_XJT(moduleIdx)) { - lcdDrawTextAlignedLeft(y, STR_FAILSAFE); - lcdDrawTextAlignedLeft(y, TR_FAILSAFE); - lcdDrawTextAtIndex(MODEL_SETUP_2ND_COLUMN, y, STR_VFAILSAFE, moduleData.failsafeMode, menuHorizontalPosition == 0 - ? attr : 0); - if (moduleData.failsafeMode == FAILSAFE_CUSTOM) - lcdDrawText(MODEL_SETUP_2ND_COLUMN + MODEL_SETUP_SET_FAILSAFE_OFS, y, STR_SET, menuHorizontalPosition == 1 - ? attr : 0); - if (attr) { - if (moduleData.failsafeMode != FAILSAFE_CUSTOM) - menuHorizontalPosition = 0; - if (menuHorizontalPosition == 0) { - if (editMode > 0 || p1valdiff) { - CHECK_INCDEC_MODELVAR_ZERO(event, moduleData.failsafeMode, FAILSAFE_LAST); - if (checkIncDec_Ret) SEND_FAILSAFE_NOW(moduleIdx); - } - } - else if (menuHorizontalPosition == 1) { - s_editMode = 0; - if (moduleData.failsafeMode == FAILSAFE_CUSTOM && event == EVT_KEY_FIRST(KEY_ENTER)) { - g_moduleIdx = moduleIdx; - pushMenu(menuModelFailsafe); - } + ModuleData &moduleData = g_model.moduleData[moduleIdx]; + lcdDrawTextAlignedLeft(y, STR_FAILSAFE); + lcdDrawTextAtIndex(MODEL_SETUP_2ND_COLUMN, y, STR_VFAILSAFE, moduleData.failsafeMode, menuHorizontalPosition == 0 ? attr : 0); + if (moduleData.failsafeMode == FAILSAFE_CUSTOM) + lcdDrawText(MODEL_SETUP_2ND_COLUMN + MODEL_SETUP_SET_FAILSAFE_OFS, y, STR_SET, menuHorizontalPosition == 1 ? attr : 0); + if (attr) { + if (moduleData.failsafeMode != FAILSAFE_CUSTOM) + menuHorizontalPosition = 0; + if (menuHorizontalPosition == 0) { + if (editMode > 0 || p1valdiff) { + CHECK_INCDEC_MODELVAR_ZERO(event, moduleData.failsafeMode, FAILSAFE_LAST); + if (checkIncDec_Ret) SEND_FAILSAFE_NOW(moduleIdx); } - else { - lcdDrawSolidFilledRect(MODEL_SETUP_2ND_COLUMN, y, LCD_W - MODEL_SETUP_2ND_COLUMN, 8); + } else if (menuHorizontalPosition == 1) { + s_editMode = 0; + if (moduleData.failsafeMode == FAILSAFE_CUSTOM && event == EVT_KEY_FIRST(KEY_ENTER)) { + g_moduleIdx = moduleIdx; + pushMenu(menuModelFailsafe); } + } else { + lcdDrawSolidFilledRect(MODEL_SETUP_2ND_COLUMN, y, LCD_W - MODEL_SETUP_2ND_COLUMN, 8); } } + } + break; + + case ITEM_MODEL_EXTERNAL_MODULE_OPTIONS: + { + uint8_t moduleIdx = CURRENT_MODULE_EDITED(k); #if defined(MULTIMODULE) - else if (IS_MODULE_MULTIMODULE(moduleIdx)) { - int optionValue = g_model.moduleData[moduleIdx].multi.optionValue; + if (IS_MODULE_MULTIMODULE(moduleIdx)) { + int optionValue = g_model.moduleData[moduleIdx].multi.optionValue; const uint8_t multi_proto = g_model.moduleData[EXTERNAL_MODULE].getMultiProtocol(true); - const mm_protocol_definition* pdef = getMultiProtocolDefinition(multi_proto); + const mm_protocol_definition * pdef = getMultiProtocolDefinition(multi_proto); if (pdef->optionsstr) lcdDrawTextAlignedLeft(y, pdef->optionsstr); @@ -1010,36 +1144,86 @@ if (attr) { if (multi_proto == MM_RF_PROTO_FS_AFHDS2A) { CHECK_INCDEC_MODELVAR(event, g_model.moduleData[moduleIdx].multi.optionValue, 0, 70); - } else if (multi_proto == MM_RF_PROTO_OLRS) { + } + else if (multi_proto == MM_RF_PROTO_OLRS) { CHECK_INCDEC_MODELVAR(event, g_model.moduleData[moduleIdx].multi.optionValue, -1, 7); - } else { + } + else { CHECK_INCDEC_MODELVAR(event, g_model.moduleData[moduleIdx].multi.optionValue, -128, 127); } } } #endif + if (IS_MODULE_R9M_FCC(moduleIdx)) { + if (IS_TELEMETRY_INTERNAL_MODULE()) { + lcdDrawTextAlignedLeft(y, STR_MODULE_TELEMETRY); + lcdDrawText(MODEL_SETUP_2ND_COLUMN, y, STR_DISABLE_INTERNAL); + } + else { + g_model.moduleData[moduleIdx].pxx.sport_out = editCheckBox(g_model.moduleData[EXTERNAL_MODULE].pxx.sport_out, MODEL_SETUP_2ND_COLUMN, y, STR_MODULE_TELEMETRY, attr, event); + } + } + else if (IS_MODULE_R9M_LBT(moduleIdx)) { + if (IS_TELEMETRY_INTERNAL_MODULE()) { + lcdDrawTextAlignedLeft(y, STR_MODULE_TELEMETRY); + lcdDrawText(MODEL_SETUP_2ND_COLUMN, y, STR_DISABLE_INTERNAL); + } + else { + lcdDrawTextAlignedLeft(y, STR_MODULE_TELEMETRY); + lcdDrawText(MODEL_SETUP_2ND_COLUMN, y, STR_BINDING_OPTION); + } + } + else if (IS_MODULE_SBUS(moduleIdx)) { + lcdDrawTextAlignedLeft(y, STR_WARN_BATTVOLTAGE); + putsVolts(lcdLastRightPos, y, getBatteryVoltage(), attr | PREC2 | LEFT); + } + break; + } + + case ITEM_MODEL_EXTERNAL_MODULE_POWER: + { + uint8_t moduleIdx = CURRENT_MODULE_EDITED(k); + if (IS_MODULE_R9M_FCC(moduleIdx)) { + // Power selection is only available on R9M FCC + lcdDrawTextAlignedLeft(y, TR_MULTI_RFPOWER); + lcdDrawTextAtIndex(MODEL_SETUP_2ND_COLUMN, y, STR_R9M_FCC_POWER_VALUES, g_model.moduleData[moduleIdx].pxx.power, LEFT | attr); + if (attr) + CHECK_INCDEC_MODELVAR(event, g_model.moduleData[moduleIdx].pxx.power, 0, R9M_FCC_POWER_MAX); + } +#if defined(MULTIMODULE) + else if (IS_MODULE_MULTIMODULE(moduleIdx)) { + g_model.moduleData[EXTERNAL_MODULE].multi.lowPowerMode = editCheckBox(g_model.moduleData[EXTERNAL_MODULE].multi.lowPowerMode, MODEL_SETUP_2ND_COLUMN, y, STR_MULTI_LOWPOWER, attr, event); + } +#endif + } break; #if defined(MULTIMODULE) - case ITEM_MODEL_EXTERNAL_MODULE_AUTOBIND: - if (g_model.moduleData[EXTERNAL_MODULE].getMultiProtocol(true) == MM_RF_PROTO_DSM2) - g_model.moduleData[EXTERNAL_MODULE].multi.autoBindMode = editCheckBox(g_model.moduleData[EXTERNAL_MODULE].multi.autoBindMode, MODEL_SETUP_2ND_COLUMN, y, STR_MULTI_DSM_AUTODTECT, attr, event); - else - g_model.moduleData[EXTERNAL_MODULE].multi.autoBindMode = editCheckBox(g_model.moduleData[EXTERNAL_MODULE].multi.autoBindMode, MODEL_SETUP_2ND_COLUMN, y, STR_MULTI_AUTOBIND, attr, event); - break; - case ITEM_MODEL_EXTERNAL_MODULE_LOWPOWER: - g_model.moduleData[EXTERNAL_MODULE].multi.lowPowerMode = editCheckBox(g_model.moduleData[EXTERNAL_MODULE].multi.lowPowerMode, MODEL_SETUP_2ND_COLUMN, y, STR_MULTI_LOWPOWER, attr, event); - break; - case ITEM_MODEL_EXTERNAL_MODULE_STATUS: { - lcdDrawTextAlignedLeft(y, STR_MODULE_STATUS); + case ITEM_MODEL_EXTERNAL_MODULE_AUTOBIND: + if (g_model.moduleData[EXTERNAL_MODULE].getMultiProtocol(true) == MM_RF_PROTO_DSM2) + g_model.moduleData[EXTERNAL_MODULE].multi.autoBindMode = editCheckBox(g_model.moduleData[EXTERNAL_MODULE].multi.autoBindMode, MODEL_SETUP_2ND_COLUMN, y, STR_MULTI_DSM_AUTODTECT, attr, event); + else + g_model.moduleData[EXTERNAL_MODULE].multi.autoBindMode = editCheckBox(g_model.moduleData[EXTERNAL_MODULE].multi.autoBindMode, MODEL_SETUP_2ND_COLUMN, y, STR_MULTI_AUTOBIND, attr, event); + break; - char statusText[64]; - multiModuleStatus.getStatusString(statusText); - lcdDrawText(MODEL_SETUP_2ND_COLUMN, y, statusText); - break; - } + case ITEM_MODEL_EXTERNAL_MODULE_STATUS: { + lcdDrawTextAlignedLeft(y, STR_MODULE_STATUS); + + char statusText[64]; + multiModuleStatus.getStatusString(statusText); + lcdDrawText(MODEL_SETUP_2ND_COLUMN, y, statusText); + break; + } + case ITEM_MODEL_EXTERNAL_MODULE_SYNCSTATUS: { + lcdDrawTextAlignedLeft(y, STR_MODULE_SYNC); + + char statusText[64]; + multiSyncStatus.getRefreshString(statusText); + lcdDrawText(MODEL_SETUP_2ND_COLUMN, y, statusText); + break; + } #endif #endif diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/128x64/model_special_functions.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/128x64/model_special_functions.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/128x64/model_special_functions.cpp 2017-05-14 17:18:57.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/128x64/model_special_functions.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -187,11 +187,11 @@ #if defined(CPUARM) if (sub==k && menuHorizontalPosition < 1 && CFN_SWITCH(cfn) == SWSRC_NONE) { drawSwitch(MODEL_SPECIAL_FUNC_1ST_COLUMN, y, CFN_SWITCH(cfn), attr | INVERS | ((functionsContext->activeSwitches & ((MASK_CFN_TYPE)1 << k)) ? BOLD : 0)); - if (active) CHECK_INCDEC_SWITCH(event, CFN_SWITCH(cfn), SWSRC_FIRST, functionsContext == &globalFunctionsContext ? SWSRC_TELEMETRY_STREAMING : SWSRC_LAST, eeFlags, isSwitchAvailableInCustomFunctions); + if (active) CHECK_INCDEC_SWITCH(event, CFN_SWITCH(cfn), SWSRC_FIRST, SWSRC_LAST, eeFlags, isSwitchAvailableInCustomFunctions); } else { drawSwitch(MODEL_SPECIAL_FUNC_1ST_COLUMN, y, CFN_SWITCH(cfn), attr | ((functionsContext->activeSwitches & ((MASK_CFN_TYPE)1 << k)) ? BOLD : 0)); - if (active || AUTOSWITCH_ENTER_LONG()) CHECK_INCDEC_SWITCH(event, CFN_SWITCH(cfn), SWSRC_FIRST, functionsContext == &globalFunctionsContext ? SWSRC_TELEMETRY_STREAMING : SWSRC_LAST, eeFlags, isSwitchAvailableInCustomFunctions); + if (active || AUTOSWITCH_ENTER_LONG()) CHECK_INCDEC_SWITCH(event, CFN_SWITCH(cfn), SWSRC_FIRST, SWSRC_LAST, eeFlags, isSwitchAvailableInCustomFunctions); } #else drawSwitch(MODEL_SPECIAL_FUNC_1ST_COLUMN, y, CFN_SWITCH(cfn), attr | ((functionsContext->activeSwitches & ((MASK_CFN_TYPE)1 << k)) ? BOLD : 0)); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/128x64/model_telemetry.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/128x64/model_telemetry.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/128x64/model_telemetry.cpp 2017-04-27 08:57:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/128x64/model_telemetry.cpp 2017-11-10 17:23:25.000000000 +0000 @@ -41,6 +41,7 @@ ITEM_TELEMETRY_RSSI_ALARM1, ITEM_TELEMETRY_RSSI_ALARM2, #if defined(CPUARM) + ITEM_TELEMETRY_DISABLE_ALARMS, ITEM_TELEMETRY_SENSORS_LABEL, ITEM_TELEMETRY_SENSOR1, ITEM_TELEMETRY_SENSOR2, @@ -91,11 +92,12 @@ ITEM_TELEMETRY_FAS_OFFSET, #endif #endif - CASE_VARIO(ITEM_TELEMETRY_VARIO_LABEL) #if defined(VARIO) + ITEM_TELEMETRY_VARIO_LABEL, ITEM_TELEMETRY_VARIO_SOURCE, + ITEM_TELEMETRY_VARIO_RANGE, + ITEM_TELEMETRY_VARIO_CENTER, #endif - CASE_VARIO(ITEM_TELEMETRY_VARIO_RANGE) #if !defined(CPUARM) // TODO check the cost of moving them to a new screen on the 9X ITEM_TELEMETRY_SCREEN_LABEL1, @@ -150,7 +152,7 @@ #endif #if defined(CPUARM) - #define RSSI_ROWS LABEL(RSSI), 0, 0, + #define RSSI_ROWS LABEL(RSSI), 0, 0, 1, #else #define RSSI_ROWS LABEL(RSSI), 1, 1, #endif @@ -162,14 +164,16 @@ #endif #if defined(PCBSTD) - #define VARIO_RANGE_ROWS 1 + #define VARIO_ROWS 1, +#elif defined(CPUARM) + #define VARIO_ROWS LABEL(Vario), 0, 1, 2, #else - #define VARIO_RANGE_ROWS (NAVIGATION_LINE_BY_LINE | 3) + #define VARIO_ROWS LABEL(Vario), 0, 1, 1, #endif #if defined (PCBTARANIS) - #define TELEMETRY_TYPE_SHOW_TELEMETRY (g_model.moduleData[INTERNAL_MODULE].rfProtocol == RF_PROTO_OFF && g_model.moduleData[EXTERNAL_MODULE].type == MODULE_TYPE_PPM) ? (uint8_t)0 : HIDDEN_ROW + #define TELEMETRY_TYPE_SHOW_TELEMETRY (! IS_INTERNAL_MODULE_ENABLED() && g_model.moduleData[EXTERNAL_MODULE].type == MODULE_TYPE_PPM) ? (uint8_t)0 : HIDDEN_ROW #elif defined (CPUARM) #define TELEMETRY_TYPE_SHOW_TELEMETRY (g_model.moduleData[EXTERNAL_MODULE].type == MODULE_TYPE_PPM) ? (uint8_t)0 : HIDDEN_ROW #endif @@ -214,13 +218,14 @@ #define SENSOR_2ND_COLUMN (12*FW) #define SENSOR_3RD_COLUMN (18*FW) -#define SENSOR_UNIT_ROWS (sensor->isConfigurable() ? (uint8_t)0 : HIDDEN_ROW) -#define SENSOR_PREC_ROWS (sensor->isConfigurable() ? (uint8_t)0 : HIDDEN_ROW) +#define SENSOR_UNIT_ROWS ((sensor->type == TELEM_TYPE_CALCULATED && (sensor->formula == TELEM_FORMULA_DIST)) || sensor->isConfigurable() ? (uint8_t)0 : HIDDEN_ROW) +#define SENSOR_PREC_ROWS (sensor->isPrecConfigurable() && sensor->unit != UNIT_FAHRENHEIT ? (uint8_t)0 : HIDDEN_ROW) #define SENSOR_PARAM1_ROWS (sensor->unit >= UNIT_FIRST_VIRTUAL ? HIDDEN_ROW : (uint8_t)0) -#define SENSOR_PARAM2_ROWS (sensor->unit == UNIT_RPMS || sensor->unit == UNIT_GPS || sensor->unit == UNIT_DATETIME || sensor->unit == UNIT_CELLS || (sensor->type==TELEM_TYPE_CALCULATED && (sensor->formula==TELEM_FORMULA_CONSUMPTION || sensor->formula==TELEM_FORMULA_TOTALIZE)) ? HIDDEN_ROW : (uint8_t)0) +#define SENSOR_PARAM2_ROWS (sensor->unit == UNIT_GPS || sensor->unit == UNIT_DATETIME || sensor->unit == UNIT_CELLS || (sensor->type==TELEM_TYPE_CALCULATED && (sensor->formula==TELEM_FORMULA_CONSUMPTION || sensor->formula==TELEM_FORMULA_TOTALIZE)) ? HIDDEN_ROW : (uint8_t)0) #define SENSOR_PARAM3_ROWS (sensor->type == TELEM_TYPE_CALCULATED && sensor->formula < TELEM_FORMULA_MULTIPLY) ? (uint8_t)0 : HIDDEN_ROW #define SENSOR_PARAM4_ROWS (sensor->type == TELEM_TYPE_CALCULATED && sensor->formula < TELEM_FORMULA_MULTIPLY) ? (uint8_t)0 : HIDDEN_ROW -#define SENSOR_AUTOOFFSET_ROWS (sensor->isConfigurable() ? (uint8_t)0 : HIDDEN_ROW) +#define SENSOR_AUTOOFFSET_ROWS (sensor->unit != UNIT_RPMS && sensor->isConfigurable() ? (uint8_t)0 : HIDDEN_ROW) +#define SENSOR_ONLYPOS_ROWS (sensor->isConfigurable() ? (uint8_t)0 : HIDDEN_ROW) #define SENSOR_FILTER_ROWS (sensor->isConfigurable() ? (uint8_t)0 : HIDDEN_ROW) #define SENSOR_PERSISTENT_ROWS (sensor->type == TELEM_TYPE_CALCULATED ? (uint8_t)0 : HIDDEN_ROW) @@ -228,7 +233,7 @@ { TelemetrySensor * sensor = & g_model.telemetrySensors[s_currIdx]; - SUBMENU(STR_MENUSENSOR, SENSOR_FIELD_MAX, {0, 0, sensor->type == TELEM_TYPE_CALCULATED ? (uint8_t)0 : (uint8_t)1, SENSOR_UNIT_ROWS, SENSOR_PREC_ROWS, SENSOR_PARAM1_ROWS, SENSOR_PARAM2_ROWS, SENSOR_PARAM3_ROWS, SENSOR_PARAM4_ROWS, SENSOR_AUTOOFFSET_ROWS, SENSOR_FILTER_ROWS, SENSOR_PERSISTENT_ROWS, 0 }); + SUBMENU(STR_MENUSENSOR, SENSOR_FIELD_MAX, {0, 0, sensor->type == TELEM_TYPE_CALCULATED ? (uint8_t)0 : (uint8_t)1, SENSOR_UNIT_ROWS, SENSOR_PREC_ROWS, SENSOR_PARAM1_ROWS, SENSOR_PARAM2_ROWS, SENSOR_PARAM3_ROWS, SENSOR_PARAM4_ROWS, SENSOR_AUTOOFFSET_ROWS, SENSOR_ONLYPOS_ROWS, SENSOR_FILTER_ROWS, SENSOR_PERSISTENT_ROWS, 0 }); lcdDrawNumber(PSIZE(TR_MENUSENSOR)*FW+1, 0, s_currIdx+1, INVERS|LEFT); if (!isGPSSensor(s_currIdx+1)) drawSensorCustomValue(SENSOR_2ND_COLUMN, 0, s_currIdx, getValue(MIXSRC_FIRST_TELEM+3*s_currIdx), LEFT); @@ -381,6 +386,12 @@ break; } } + else if (sensor->unit == UNIT_RPMS) { + lcdDrawTextAlignedLeft(y, STR_MULTIPLIER); + if (attr) sensor->custom.offset = checkIncDec(event, sensor->custom.offset, 1, 30000, EE_MODEL|NO_INCDEC_MARKS|INCDEC_REP10); + lcdDrawNumber(SENSOR_2ND_COLUMN, y, sensor->custom.offset, LEFT|attr); + break; + } else { lcdDrawTextAlignedLeft(y, NO_INDENT(STR_OFFSET)); if (attr) CHECK_INCDEC_MODELVAR(event, sensor->custom.offset, -30000, +30000); @@ -424,10 +435,16 @@ case SENSOR_FIELD_PERSISTENT: ON_OFF_MENU_ITEM(sensor->persistent, SENSOR_2ND_COLUMN, y, NO_INDENT(STR_PERSISTENT), attr, event); + if (checkIncDec_Ret && !sensor->persistent) { + sensor->persistentValue = 0; + } break; case SENSOR_FIELD_LOGS: ON_OFF_MENU_ITEM(sensor->logs, SENSOR_2ND_COLUMN, y, STR_LOGS, attr, event); + if (attr && checkIncDec_Ret) { + logsClose(); + } break; } @@ -480,7 +497,7 @@ } #endif - MENU(STR_MENUTELEMETRY, menuTabModel, MENU_MODEL_TELEMETRY_FRSKY, HEADER_LINE+ITEM_TELEMETRY_MAX, { HEADER_LINE_COLUMNS TELEMETRY_TYPE_ROWS CHANNELS_ROWS RSSI_ROWS SENSORS_ROWS USRDATA_ROWS CASE_VARIO(LABEL(Vario)) CASE_VARIO(0) CASE_VARIO(VARIO_RANGE_ROWS) TELEMETRY_SCREENS_ROWS }); + MENU(STR_MENUTELEMETRY, menuTabModel, MENU_MODEL_TELEMETRY_FRSKY, HEADER_LINE+ITEM_TELEMETRY_MAX, { HEADER_LINE_COLUMNS TELEMETRY_TYPE_ROWS CHANNELS_ROWS RSSI_ROWS SENSORS_ROWS USRDATA_ROWS VARIO_ROWS TELEMETRY_SCREENS_ROWS }); uint8_t sub = menuVerticalPosition - HEADER_LINE; @@ -522,7 +539,7 @@ lcdDrawChar(lcdLastRightPos, y, ':', attr); lcdDrawSizedText(3*FW, y, g_model.telemetrySensors[index].label, TELEM_LABEL_LEN, ZCHAR); if (telemetryItems[index].isFresh()) { - lcdDrawChar(16*FW, y, '*'); + lcdDrawChar(17*FW, y, '*'); } TelemetryItem & telemetryItem = telemetryItems[index]; if (telemetryItem.isAvailable()) { @@ -701,14 +718,18 @@ case ITEM_TELEMETRY_RSSI_ALARM1: case ITEM_TELEMETRY_RSSI_ALARM2: { - uint8_t alarm = k-ITEM_TELEMETRY_RSSI_ALARM1; #if defined(CPUARM) - lcdDrawTextAlignedLeft(y, (alarm==0 ? STR_LOWALARM : STR_CRITICALALARM)); - lcdDrawNumber(LCD_W, y, getRssiAlarmValue(alarm), RIGHT | attr, 3); + bool warning = (k==ITEM_TELEMETRY_RSSI_ALARM1); + lcdDrawTextAlignedLeft(y, (warning ? STR_LOWALARM : STR_CRITICALALARM)); + lcdDrawNumber(LCD_W, y, warning? g_model.rssiAlarms.getWarningRssi() : g_model.rssiAlarms.getCriticalRssi(), RIGHT | attr, 3); if (attr && s_editMode>0) { - CHECK_INCDEC_MODELVAR(event, g_model.frsky.rssiAlarms[alarm].value, -30, 30); - } + if (warning) + CHECK_INCDEC_MODELVAR(event, g_model.rssiAlarms.warning, -30, 30); + else + CHECK_INCDEC_MODELVAR(event, g_model.rssiAlarms.critical, -30, 30); + } #else // CPUARM + uint8_t alarm = (k-ITEM_TELEMETRY_RSSI_ALARM1); lcdDrawTextAlignedLeft(y, STR_ALARM); lcdDrawTextAtIndex(TELEM_COL2, y, STR_VALARM, ((2+alarm+g_model.frsky.rssiAlarms[alarm].level)%4), menuHorizontalPosition<=0 ? attr : 0); lcdDrawChar(TELEM_COL2+4*FW, y, '<'); @@ -726,7 +747,11 @@ #endif // CPUARM break; } - +#if defined(CPUARM) + case ITEM_TELEMETRY_DISABLE_ALARMS: + g_model.rssiAlarms.disabled = editCheckBox(g_model.rssiAlarms.disabled, LCD_W - 10, y, STR_DISABLE_ALARM, attr, event); + break; +#endif #if !defined(CPUARM) #if defined(FRSKY_HUB) || defined(WS_HOW_HIGH) case ITEM_TELEMETRY_USR_LABEL: @@ -787,9 +812,10 @@ #endif break; - case ITEM_TELEMETRY_VARIO_RANGE: - lcdDrawTextAlignedLeft(y, STR_LIMIT); #if defined(PCBSTD) + case ITEM_TELEMETRY_VARIO_RANGE: + lcdDrawTextAlignedLeft(y, STR_RANGE); + lcdDrawNumber(TELEM_COL2, y, 5+g_model.frsky.varioCenterMax, (menuHorizontalPosition==0 ? attr : 0)|PREC1|LEFT); lcdDrawNumber(TELEM_COL2+8*FW, y, 10+g_model.frsky.varioMax, (menuHorizontalPosition==1 ? attr : 0)); if (attr && (s_editMode>0 || p1valdiff)) { @@ -802,33 +828,52 @@ break; } } + break; #else + case ITEM_TELEMETRY_VARIO_RANGE: + lcdDrawTextAlignedLeft(y, STR_RANGE); if (attr && CURSOR_ON_LINE()) { lcdDrawSolidFilledRect(TELEM_COL2-1, y-1, LCD_W-TELEM_COL2+1, FH+1); } lcdDrawNumber(TELEM_COL2, y, -10+g_model.frsky.varioMin, ((CURSOR_ON_LINE() || menuHorizontalPosition==0) ? attr : 0)|LEFT); - lcdDrawNumber(TELEM_COL2+4*FW-2, y, -5+g_model.frsky.varioCenterMin, ((CURSOR_ON_LINE() || menuHorizontalPosition==1) ? attr : 0)|PREC1|LEFT); - lcdDrawNumber(TELEM_COL2+8*FW-1, y, 5+g_model.frsky.varioCenterMax, ((CURSOR_ON_LINE() || menuHorizontalPosition==2) ? attr : 0)|PREC1|LEFT); - lcdDrawNumber(TELEM_COL2+12*FW-4, y, 10+g_model.frsky.varioMax, ((CURSOR_ON_LINE() || menuHorizontalPosition==3) ? attr : 0)|LEFT); + lcdDrawNumber(TELEM_COL2+4*FW, y, 10+g_model.frsky.varioMax, ((CURSOR_ON_LINE() || menuHorizontalPosition==1) ? attr : 0)|LEFT); if (attr && (s_editMode>0 || p1valdiff)) { switch (menuHorizontalPosition) { case 0: CHECK_INCDEC_MODELVAR(event, g_model.frsky.varioMin, -7, 7); break; case 1: + CHECK_INCDEC_MODELVAR(event, g_model.frsky.varioMax, -7, 7); + break; + } + } + break; + + case ITEM_TELEMETRY_VARIO_CENTER: + lcdDrawTextAlignedLeft(y, STR_CENTER); + lcdDrawNumber(TELEM_COL2, y, -5+g_model.frsky.varioCenterMin, ((CURSOR_ON_LINE() || menuHorizontalPosition==0) ? attr : 0)|PREC1|LEFT); + lcdDrawNumber(TELEM_COL2+4*FW, y, 5+g_model.frsky.varioCenterMax, ((CURSOR_ON_LINE() || menuHorizontalPosition==1) ? attr : 0)|PREC1|LEFT); +#if defined(CPUARM) + lcdDrawTextAtIndex(TELEM_COL2+8*FW, y, STR_VVARIOCENTER, g_model.frsky.varioCenterSilent, (menuHorizontalPosition==2 ? attr : 0)); +#endif + if (attr && (s_editMode>0 || p1valdiff)) { + switch (menuHorizontalPosition) { + case 0: CHECK_INCDEC_MODELVAR(event, g_model.frsky.varioCenterMin, -16, 5+min(10, g_model.frsky.varioCenterMax+5)); break; - case 2: + case 1: CHECK_INCDEC_MODELVAR(event, g_model.frsky.varioCenterMax, -5+max(-10, g_model.frsky.varioCenterMin-5), +15); break; - case 3: - CHECK_INCDEC_MODELVAR(event, g_model.frsky.varioMax, -7, 7); +#if defined(CPUARM) + case 2: + CHECK_INCDEC_MODELVAR_ZERO(event, g_model.frsky.varioCenterSilent, 1); break; +#endif } } -#endif break; #endif +#endif #if !defined(CPUARM) case ITEM_TELEMETRY_SCREEN_LABEL1: diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/128x64/popups.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/128x64/popups.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/128x64/popups.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/128x64/popups.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -60,7 +60,7 @@ void drawAlertBox(const pm_char * title, const pm_char * text, const char * action) { lcdClear(); - lcd_img(2, 0, ASTERISK_BITMAP, 0, 0); + lcdDraw1bitBitmap(2, 0, ASTERISK_BITMAP, 0, 0); #define MESSAGE_LCD_OFFSET 6*FW @@ -92,6 +92,8 @@ lcdRefresh(); lcdSetContrast(); clearKeyEvents(); + backlightOn(); + checkBacklight(); } void runPopupWarning(event_t event) diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/128x64/radio_diaganas.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/128x64/radio_diaganas.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/128x64/radio_diaganas.cpp 2017-04-29 16:57:04.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/128x64/radio_diaganas.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -66,7 +66,7 @@ lcdDrawTextAlignedLeft(MENU_HEADER_HEIGHT + 1 + (NUM_STICKS+NUM_POTS+NUM_SLIDERS+1)/2 * FH + 2, STR_BATT_CALIB); putsVolts(LEN_CALIB_FIELDS*FW+FW, MENU_HEADER_HEIGHT + 1 + (NUM_STICKS+NUM_POTS+NUM_SLIDERS+1)/2 * FH + 2, getBatteryVoltage(), (menuVerticalPosition==HEADER_LINE ? INVERS | (s_editMode > 0 ? BLINK : 0) : 0) | PREC2 | LEFT); // SWR - if(IS_MODULE_XJT(EXTERNAL_MODULE) && !IS_INTERNAL_MODULE_ON()) { + if(IS_MODULE_PXX(EXTERNAL_MODULE) && !IS_INTERNAL_MODULE_ON()) { lcdDrawTextAlignedLeft(MENU_HEADER_HEIGHT + 1 + (NUM_STICKS+NUM_POTS+NUM_SLIDERS+1)/2 * FH + 1 * FH + 2, "RAS"); lcdDrawNumber(LEN_CALIB_FIELDS*FW+FW, MENU_HEADER_HEIGHT + 1 + (NUM_STICKS+NUM_POTS+NUM_SLIDERS+1)/2 * FH + 1 * FH + 2, telemetryData.swr.value, LEFT); } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/128x64/radio_diagkeys.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/128x64/radio_diagkeys.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/128x64/radio_diagkeys.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/128x64/radio_diagkeys.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -2,7 +2,7 @@ * Copyright (C) OpenTX * * Based on code named - * th9x - http://code.google.com/p/th9x + * th9x - http://code.google.com/p/th9x * er9x - http://code.google.com/p/er9x * gruvin9x - http://code.google.com/p/gruvin9x * @@ -45,22 +45,29 @@ if (i < 8) { y = MENU_HEADER_HEIGHT + FH*3 + FH*(i/2); - if (i&1) lcd_img(14*FW, y, sticks, i/2, 0); + if (i&1) lcdDraw1bitBitmap(14*FW, y, sticks, i/2, 0); displayKeyState(i&1? 20*FW : 18*FW, y, TRM_BASE+i); } if (i < 6) { y = MENU_HEADER_HEIGHT + FH + FH*i; +#if defined(PCBX7) + if (i > 1) { + lcdDrawTextAtIndex(0, y, STR_VKEYS, (5-i), 0); + displayKeyState(5*FW+4, y, KEY_MENU+(5-i)); + } +#else lcdDrawTextAtIndex(0, y, STR_VKEYS, (5-i), 0); displayKeyState(5*FW+2, y, KEY_MENU+(5-i)); +#endif } - + #if defined(PCBTARANIS) if (i < NUM_SWITCHES) { if (SWITCH_EXISTS(i)) { getvalue_t val = getValue(MIXSRC_FIRST_SWITCH+i); getvalue_t sw = ((val < 0) ? 3*i+1 : ((val == 0) ? 3*i+2 : 3*i+3)); - drawSwitch(8*FW, y, sw, 0); + drawSwitch(8*FW+4, y, sw, 0); } } #else @@ -74,12 +81,22 @@ #if defined(ROTARY_ENCODER_NAVIGATION) for (uint8_t i=0; i 0 && menuHorizontalPosition == 0)) - editName(HW_SETTINGS_COLUMN, y, g_eeGeneral.anaNames[NUM_STICKS+idx], LEN_ANA_NAME, event, attr && menuHorizontalPosition == 0); + editName(HW_SETTINGS_COLUMN1, y, g_eeGeneral.anaNames[NUM_STICKS+idx], LEN_ANA_NAME, event, attr && menuHorizontalPosition == 0); else - lcdDrawMMM(HW_SETTINGS_COLUMN, y, menuHorizontalPosition==0 ? attr : 0); + lcdDrawMMM(HW_SETTINGS_COLUMN1, y, menuHorizontalPosition==0 ? attr : 0); uint8_t potType = (g_eeGeneral.potsConfig & mask) >> shift; - potType = editChoice(HW_SETTINGS_COLUMN+5*FW, y, "", STR_POTTYPES, potType, POT_NONE, POT_WITHOUT_DETENT, menuHorizontalPosition == 1 ? attr : 0, event); + potType = editChoice(HW_SETTINGS_COLUMN2, y, "", STR_POTTYPES, potType, POT_NONE, POT_WITHOUT_DETENT, menuHorizontalPosition == 1 ? attr : 0, event); g_eeGeneral.potsConfig &= ~mask; g_eeGeneral.potsConfig |= (potType << shift); break; @@ -171,6 +187,7 @@ case ITEM_RADIO_HARDWARE_LABEL_SWITCHES: lcdDrawTextAlignedLeft(y, STR_SWITCHES); break; + case ITEM_RADIO_HARDWARE_SA: case ITEM_RADIO_HARDWARE_SB: case ITEM_RADIO_HARDWARE_SC: @@ -182,10 +199,10 @@ int config = SWITCH_CONFIG(index); lcdDrawTextAtIndex(INDENT_WIDTH, y, STR_VSRCRAW, MIXSRC_FIRST_SWITCH-MIXSRC_Rud+index+1, menuHorizontalPosition < 0 ? attr : 0); if (ZEXIST(g_eeGeneral.switchNames[index]) || (attr && s_editMode > 0 && menuHorizontalPosition == 0)) - editName(HW_SETTINGS_COLUMN, y, g_eeGeneral.switchNames[index], LEN_SWITCH_NAME, event, menuHorizontalPosition == 0 ? attr : 0); + editName(HW_SETTINGS_COLUMN1, y, g_eeGeneral.switchNames[index], LEN_SWITCH_NAME, event, menuHorizontalPosition == 0 ? attr : 0); else - lcdDrawMMM(HW_SETTINGS_COLUMN, y, menuHorizontalPosition == 0 ? attr : 0); - config = editChoice(HW_SETTINGS_COLUMN+5*FW, y, "", STR_SWTYPES, config, SWITCH_NONE, SWITCH_TYPE_MAX(index), menuHorizontalPosition == 1 ? attr : 0, event); + lcdDrawMMM(HW_SETTINGS_COLUMN1, y, menuHorizontalPosition == 0 ? attr : 0); + config = editChoice(HW_SETTINGS_COLUMN2, y, "", STR_SWTYPES, config, SWITCH_NONE, SWITCH_TYPE_MAX(index), menuHorizontalPosition == 1 ? attr : 0, event); if (attr && checkIncDec_Ret) { swconfig_t mask = (swconfig_t)0x03 << (2*index); g_eeGeneral.switchConfig = (g_eeGeneral.switchConfig & ~mask) | ((swconfig_t(config) & 0x03) << (2*index)); @@ -193,10 +210,56 @@ break; } + case ITEM_RADIO_HARDWARE_SERIAL_BAUDRATE: + lcdDrawTextAlignedLeft(y, STR_MAXBAUDRATE); + lcdDrawNumber(HW_SETTINGS_COLUMN2, y, CROSSFIRE_BAUDRATES[g_eeGeneral.telemetryBaudrate], attr|LEFT); + if (attr) { + g_eeGeneral.telemetryBaudrate = DIM(CROSSFIRE_BAUDRATES) - 1 - checkIncDecModel(event, DIM(CROSSFIRE_BAUDRATES) - 1 - g_eeGeneral.telemetryBaudrate, 0, DIM(CROSSFIRE_BAUDRATES) - 1); + if (checkIncDec_Ret) { + pauseMixerCalculations(); + pausePulses(); + EXTERNAL_MODULE_OFF(); + CoTickDelay(10); // 20ms so that the pulses interrupt will reinit the frame rate + telemetryProtocol = 255; // force telemetry port + module reinitialization + EXTERNAL_MODULE_ON(); + resumePulses(); + resumeMixerCalculations(); + } + } + break; + +#if defined(BLUETOOTH) + case ITEM_RADIO_HARDWARE_BLUETOOTH_MODE: + lcdDrawTextAlignedLeft(y, STR_BLUETOOTH); + lcdDrawTextAtIndex(HW_SETTINGS_COLUMN2, y, STR_BLUETOOTH_MODES, g_eeGeneral.bluetoothMode, attr); + if ((g_eeGeneral.bluetoothMode != BLUETOOTH_OFF) && !btChipPresent) { + g_eeGeneral.bluetoothMode = BLUETOOTH_OFF; + } + if (attr) { + g_eeGeneral.bluetoothMode = checkIncDecGen(event, g_eeGeneral.bluetoothMode, BLUETOOTH_OFF, BLUETOOTH_TRAINER); + } + break; + + case ITEM_RADIO_HARDWARE_BLUETOOTH_LOCAL_ADDR: + lcdDrawTextAlignedLeft(y, INDENT "Local addr"); + lcdDrawText(HW_SETTINGS_COLUMN2, y, bluetoothLocalAddr[0] == '\0' ? "---" : bluetoothLocalAddr); + break; + + case ITEM_RADIO_HARDWARE_BLUETOOTH_DISTANT_ADDR: + lcdDrawTextAlignedLeft(y, INDENT "Dist addr"); + lcdDrawText(HW_SETTINGS_COLUMN2, y, bluetoothDistantAddr[0] == '\0' ? "---" : bluetoothDistantAddr); + break; + + case ITEM_RADIO_HARDWARE_BLUETOOTH_NAME: + lcdDrawText(INDENT_WIDTH, y, STR_NAME); + editName(HW_SETTINGS_COLUMN2, y, g_eeGeneral.bluetoothName, LEN_BLUETOOTH_NAME, event, attr); + break; +#endif + case ITEM_RADIO_HARDWARE_JITTER_FILTER: { uint8_t b = 1-g_eeGeneral.jitterFilter; - g_eeGeneral.jitterFilter = 1 - editCheckBox(b, HW_SETTINGS_COLUMN+5*FW, y, STR_JITTER_FILTER, attr, event); + g_eeGeneral.jitterFilter = 1 - editCheckBox(b, HW_SETTINGS_COLUMN2, y, STR_JITTER_FILTER, attr, event); break; } } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/128x64/radio_setup.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/128x64/radio_setup.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/128x64/radio_setup.cpp 2017-04-27 08:57:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/128x64/radio_setup.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -88,6 +88,7 @@ ITEM_SETUP_INACTIVITY_ALARM, ITEM_SETUP_MEMORY_WARNING, ITEM_SETUP_ALARM_WARNING, + CASE_CPUARM(ITEM_SETUP_RSSI_POWEROFF_ALARM) IF_ROTARY_ENCODERS(ITEM_SETUP_RE_NAVIGATION) ITEM_SETUP_BACKLIGHT_LABEL, ITEM_SETUP_BACKLIGHT_MODE, @@ -106,13 +107,14 @@ IF_FAI_CHOICE(ITEM_SETUP_FAI) CASE_MAVLINK(ITEM_MAVLINK_BAUD) CASE_CPUARM(ITEM_SETUP_SWITCHES_DELAY) + CASE_STM32(ITEM_SETUP_USB_MODE) ITEM_SETUP_RX_CHANNEL_ORD, ITEM_SETUP_STICK_MODE_LABELS, ITEM_SETUP_STICK_MODE, ITEM_SETUP_MAX }; -#if defined(FRSKY_STICKS) +#if defined(FRSKY_STICKS) && !defined(PCBTARANIS) #define COL_TX_MODE 0 #else #define COL_TX_MODE LABEL(TX_MODE) @@ -140,7 +142,7 @@ } #endif - MENU(STR_MENURADIOSETUP, menuTabGeneral, MENU_RADIO_SETUP, HEADER_LINE+ITEM_SETUP_MAX, { HEADER_LINE_COLUMNS CASE_RTCLOCK(2) CASE_RTCLOCK(2) CASE_BATTGRAPH(1) LABEL(SOUND), CASE_AUDIO(0) CASE_BUZZER(0) CASE_VOICE(0) CASE_CPUARM(0) CASE_CPUARM(0) CASE_CPUARM(0) 0, CASE_AUDIO(0) CASE_VARIO_CPUARM(LABEL(VARIO)) CASE_VARIO_CPUARM(0) CASE_VARIO_CPUARM(0) CASE_VARIO_CPUARM(0) CASE_VARIO_CPUARM(0) CASE_HAPTIC(LABEL(HAPTIC)) CASE_HAPTIC(0) CASE_HAPTIC(0) CASE_HAPTIC(0) 0, LABEL(ALARMS), 0, CASE_CAPACITY(0) CASE_PCBSKY9X(0) 0, 0, 0, IF_ROTARY_ENCODERS(0) LABEL(BACKLIGHT), 0, 0, CASE_CPUARM(0) CASE_PWM_BACKLIGHT(0) CASE_PWM_BACKLIGHT(0) 0, CASE_SPLASH_PARAM(0) CASE_GPS(0) CASE_CPUARM(0) CASE_GPS(0) CASE_PXX(0) CASE_CPUARM(0) CASE_CPUARM(0) IF_FAI_CHOICE(0) CASE_MAVLINK(0) CASE_CPUARM(0) 0, COL_TX_MODE, 0, 1/*to force edit mode*/}); + MENU(STR_MENURADIOSETUP, menuTabGeneral, MENU_RADIO_SETUP, HEADER_LINE+ITEM_SETUP_MAX, { HEADER_LINE_COLUMNS CASE_RTCLOCK(2) CASE_RTCLOCK(2) CASE_BATTGRAPH(1) LABEL(SOUND), CASE_AUDIO(0) CASE_BUZZER(0) CASE_VOICE(0) CASE_CPUARM(0) CASE_CPUARM(0) CASE_CPUARM(0) 0, CASE_AUDIO(0) CASE_VARIO_CPUARM(LABEL(VARIO)) CASE_VARIO_CPUARM(0) CASE_VARIO_CPUARM(0) CASE_VARIO_CPUARM(0) CASE_VARIO_CPUARM(0) CASE_HAPTIC(LABEL(HAPTIC)) CASE_HAPTIC(0) CASE_HAPTIC(0) CASE_HAPTIC(0) 0, LABEL(ALARMS), 0, CASE_CAPACITY(0) CASE_PCBSKY9X(0) 0, 0, 0, CASE_CPUARM(0) IF_ROTARY_ENCODERS(0) LABEL(BACKLIGHT), 0, 0, CASE_CPUARM(0) CASE_PWM_BACKLIGHT(0) CASE_PWM_BACKLIGHT(0) 0, CASE_SPLASH_PARAM(0) CASE_GPS(0) CASE_CPUARM(0) CASE_GPS(0) CASE_PXX(0) CASE_CPUARM(0) CASE_CPUARM(0) IF_FAI_CHOICE(0) CASE_MAVLINK(0) CASE_CPUARM(0) CASE_STM32(0) 0, COL_TX_MODE, 0, 1/*to force edit mode*/}); if (event == EVT_ENTRY) { reusableBuffer.generalSettings.stickMode = g_eeGeneral.stickMode; @@ -382,11 +384,20 @@ case ITEM_SETUP_ALARM_WARNING: { - uint8_t b = 1-g_eeGeneral.disableAlarmWarning; + uint8_t b = 1 - g_eeGeneral.disableAlarmWarning; g_eeGeneral.disableAlarmWarning = 1 - editCheckBox(b, RADIO_SETUP_2ND_COLUMN, y, STR_ALARMWARNING, attr, event); break; } +#if defined(CPUARM) + case ITEM_SETUP_RSSI_POWEROFF_ALARM: + { + uint8_t b = 1 - g_eeGeneral.disableRssiPoweroffAlarm; + g_eeGeneral.disableRssiPoweroffAlarm = 1 - editCheckBox(b, RADIO_SETUP_2ND_COLUMN, y, STR_RSSISHUTDOWNALARM, attr, event); + break; + } +#endif + #if defined(TX_CAPACITY_MEASUREMENT) case ITEM_SETUP_CAPACITY_WARNING: lcdDrawTextAlignedLeft(y, STR_CAPAWARNING); @@ -467,9 +478,22 @@ #if defined(SPLASH) && !defined(FSPLASH) case ITEM_SETUP_DISABLE_SPLASH: { +#if defined(CPUARM) + lcdDrawTextAlignedLeft(y, STR_SPLASHSCREEN); + if (SPLASH_NEEDED()) { + lcdDrawNumber(RADIO_SETUP_2ND_COLUMN, y, SPLASH_TIMEOUT/100, attr|LEFT); + lcdDrawChar(lcdLastRightPos, y, 's'); + } + else { + lcdDrawMMM(RADIO_SETUP_2ND_COLUMN, y, attr); + } + if (attr) g_eeGeneral.splashMode = -checkIncDecGen(event, -g_eeGeneral.splashMode, -3, 4); + break; +#else uint8_t b = 1-g_eeGeneral.splashMode; g_eeGeneral.splashMode = 1 - editCheckBox(b, RADIO_SETUP_2ND_COLUMN, y, STR_SPLASHSCREEN, attr, event); break; +#endif } #endif @@ -541,7 +565,11 @@ if (attr) CHECK_INCDEC_GENVAR(event, g_eeGeneral.switchesDelay, -15, 100-15); break; #endif - +#if defined(STM32) + case ITEM_SETUP_USB_MODE: + g_eeGeneral.USBMode = editChoice(RADIO_SETUP_2ND_COLUMN, y, STR_USBMODE, STR_USBMODES, g_eeGeneral.USBMode, USB_UNSELECTED_MODE, USB_MAX_MODE, attr, event); + break; +#endif case ITEM_SETUP_RX_CHANNEL_ORD: lcdDrawTextAlignedLeft(y, STR_RXCHANNELORD); // RAET->AETR for (uint8_t i=1; i<=4; i++) { @@ -553,14 +581,14 @@ case ITEM_SETUP_STICK_MODE_LABELS: lcdDrawTextAlignedLeft(y, NO_INDENT(STR_MODE)); for (uint8_t i=0; i<4; i++) { - lcd_img(5*FW+i*(4*FW+2), y, sticks, i, 0); -#if defined(FRSKY_STICKS) + lcdDraw1bitBitmap(5*FW+i*(4*FW+2), y, sticks, i, 0); +#if defined(FRSKY_STICKS) && !defined(PCBTARANIS) if (g_eeGeneral.stickReverse & (1< bar*(i-1)) { + lcdDrawFilledRect(RSSSI_X + i*4, RSSSI_Y - 2*i, 3, 2*i, SOLID, 0); + } + } +} +#endif + void drawPotsBars() { // Optimization by Mike Blandford @@ -453,10 +471,17 @@ displayVoltageOrAlarm(); // Timer 1 - drawTimerWithMode(120, 2*FH, 0); + drawTimerWithMode(125, 2*FH, 0); // Trims sliders displayTrims(mode); + +#if defined(TELEMETRY_FRSKY) && defined(CPUARM) + // RSSI gauge + if (TELEMETRY_RSSI() > 0) { + drawRSSIGauge(); + } +#endif } if (view_base < VIEW_INPUTS) { diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/128x64/view_statistics.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/128x64/view_statistics.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/128x64/view_statistics.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/128x64/view_statistics.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -20,17 +20,38 @@ #include "opentx.h" +#define STATS_1ST_COLUMN 1 +#define STATS_2ND_COLUMN 7*FW+FW/2 +#define STATS_3RD_COLUMN 14*FW+FW/2 +#define STATS_LABEL_WIDTH 3*FW + void menuStatisticsView(event_t event) { TITLE(STR_MENUSTAT); switch (event) { case EVT_KEY_FIRST(KEY_UP): +#if defined(PCBX7) + case EVT_KEY_BREAK(KEY_PAGE): +#endif + chainMenu(menuStatisticsDebug); + break; + + case EVT_KEY_FIRST(KEY_DOWN): +#if defined(STM32) + case EVT_KEY_LONG(KEY_PAGE): + killEvents(event); + chainMenu(menuStatisticsDebug2); +#else chainMenu(menuStatisticsDebug); +#endif break; #if defined(CPUARM) - case EVT_KEY_LONG(KEY_MENU): + case EVT_KEY_LONG(KEY_MENU): // historical +#if !defined(PCBSKY9X) + case EVT_KEY_LONG(KEY_ENTER): +#endif g_eeGeneral.globalTimer = 0; storageDirty(EE_GENERAL); sessionTimer = 0; @@ -41,8 +62,30 @@ break; } +#if defined(CPUARM) + // Session and Total timers + lcdDrawText(STATS_1ST_COLUMN, FH*1+1, "SES", BOLD); + drawTimer(STATS_1ST_COLUMN + STATS_LABEL_WIDTH, FH*1+1, sessionTimer, 0, 0); + lcdDrawText(STATS_1ST_COLUMN, FH*2+1, "TOT", BOLD); + drawTimer(STATS_1ST_COLUMN + STATS_LABEL_WIDTH, FH*2+1, g_eeGeneral.globalTimer + sessionTimer, TIMEHOUR, 0); + + // Throttle special timers + lcdDrawText(STATS_2ND_COLUMN, FH*0+1, "THR", BOLD); + drawTimer(STATS_2ND_COLUMN + STATS_LABEL_WIDTH, FH*0+1, s_timeCumThr, 0, 0); + lcdDrawText(STATS_2ND_COLUMN, FH*1+1, "TH%", BOLD); + drawTimer(STATS_2ND_COLUMN + STATS_LABEL_WIDTH, FH*1+1, s_timeCum16ThrP/16, 0, 0); + + // Timers + for (int i=0; i 3600) + drawTimer(STATS_3RD_COLUMN + STATS_LABEL_WIDTH, FH*i+1, timersStates[i].val, TIMEHOUR, 0); + else + drawTimer(STATS_3RD_COLUMN + STATS_LABEL_WIDTH, FH*i+1, timersStates[i].val, 0, 0); + } +#else lcdDrawText( 1*FW, FH*0, STR_TOTTM1TM2THRTHP); - + drawTimer( 5*FW+5*FWNUM+1, FH*1, timersStates[0].val, RIGHT, 0); drawTimer( 12*FW+5*FWNUM+1, FH*1, timersStates[1].val, RIGHT, 0); @@ -50,6 +93,7 @@ drawTimer( 12*FW+5*FWNUM+1, FH*2, s_timeCum16ThrP/16, RIGHT, 0); drawTimer( 12*FW+5*FWNUM+1, FH*0, sessionTimer, RIGHT, 0); +#endif #if defined(THRTRACE) const coord_t x = 5; @@ -72,11 +116,16 @@ #define MENU_DEBUG_COL1_OFS (11*FW-3) #define MENU_DEBUG_COL2_OFS (17*FW) #define MENU_DEBUG_Y_CURRENT (1*FH) + #define MENU_DEBUG_ROW1 (1*FH+1) + #define MENU_DEBUG_ROW2 (2*FH+1) #define MENU_DEBUG_Y_MAH (2*FH) #define MENU_DEBUG_Y_CPU_TEMP (3*FH) #define MENU_DEBUG_Y_COPROC (4*FH) #define MENU_DEBUG_Y_MIXMAX (5*FH) #define MENU_DEBUG_Y_RTOS (6*FH) + #define MENU_DEBUG_Y_USB (2*FH) + #define MENU_DEBUG_Y_LUA (3*FH) + #define MENU_DEBUG_Y_FREE_RAM (4*FH) #else #define MENU_DEBUG_COL1_OFS (14*FW) #endif @@ -98,7 +147,7 @@ killEvents(event); break; #endif - + case EVT_KEY_FIRST(KEY_ENTER): #if !defined(CPUARM) g_tmr1Latency_min = 0xff; @@ -107,13 +156,19 @@ maxMixerDuration = 0; break; -#if defined(DEBUG_TRACE_BUFFER) + case EVT_KEY_FIRST(KEY_UP): - pushMenu(menuTraceBuffer); +#if defined(STM32) + case EVT_KEY_BREAK(KEY_PAGE): + chainMenu(menuStatisticsDebug2); return; #endif case EVT_KEY_FIRST(KEY_DOWN): +#if defined(PCBX7) + case EVT_KEY_LONG(KEY_PAGE): +#endif + killEvents(event); chainMenu(menuStatisticsView); break; @@ -168,6 +223,29 @@ } #endif +#if defined(PCBTARANIS) +#if !defined(SIMU) && defined(DEBUG) + lcdDrawTextAlignedLeft(MENU_DEBUG_Y_USB, "Usb"); + lcdDrawNumber(MENU_DEBUG_COL1_OFS, MENU_DEBUG_Y_USB, charsWritten, LEFT); + lcdDrawText(lcdLastRightPos, MENU_DEBUG_Y_USB, " "); + lcdDrawNumber(lcdLastRightPos, MENU_DEBUG_Y_USB, APP_Rx_ptr_in, LEFT); + lcdDrawText(lcdLastRightPos, MENU_DEBUG_Y_USB, " "); + lcdDrawNumber(lcdLastRightPos, MENU_DEBUG_Y_USB, APP_Rx_ptr_out, LEFT); + lcdDrawText(lcdLastRightPos, MENU_DEBUG_Y_USB, " "); + lcdDrawNumber(lcdLastRightPos, MENU_DEBUG_Y_USB, usbWraps, LEFT); +#endif + lcdDrawTextAlignedLeft(MENU_DEBUG_Y_FREE_RAM, "Free Mem"); + lcdDrawNumber(MENU_DEBUG_COL1_OFS, MENU_DEBUG_Y_FREE_RAM, availableMemory(), LEFT); + lcdDrawText(lcdLastRightPos, MENU_DEBUG_Y_FREE_RAM, "b"); +#if defined(LUA) + lcdDrawTextAlignedLeft(MENU_DEBUG_Y_LUA, "Lua scripts"); + lcdDrawText(MENU_DEBUG_COL1_OFS, MENU_DEBUG_Y_LUA+1, "[D]", SMLSIZE); + lcdDrawNumber(lcdLastRightPos, MENU_DEBUG_Y_LUA, 10*maxLuaDuration, LEFT); + lcdDrawText(lcdLastRightPos+2, MENU_DEBUG_Y_LUA+1, "[I]", SMLSIZE); + lcdDrawNumber(lcdLastRightPos, MENU_DEBUG_Y_LUA, 10*maxLuaInterval, LEFT); +#endif // LUA +#endif // PCBTARANIS + #if defined(CPUARM) lcdDrawTextAlignedLeft(MENU_DEBUG_Y_MIXMAX, STR_TMIXMAXMS); lcdDrawNumber(MENU_DEBUG_COL1_OFS, MENU_DEBUG_Y_MIXMAX, DURATION_MS_PREC2(maxMixerDuration), PREC2|LEFT); @@ -176,14 +254,12 @@ #if defined(CPUARM) lcdDrawTextAlignedLeft(MENU_DEBUG_Y_RTOS, STR_FREESTACKMINB); - lcdDrawNumber(MENU_DEBUG_COL1_OFS, MENU_DEBUG_Y_RTOS+2, menusStack.available(), UNSIGN|LEFT|TINSIZE); + lcdDrawNumber(MENU_DEBUG_COL1_OFS, MENU_DEBUG_Y_RTOS, menusStack.available(), UNSIGN|LEFT); lcdDrawText(lcdLastRightPos, MENU_DEBUG_Y_RTOS, "/"); - lcdDrawNumber(lcdLastRightPos, MENU_DEBUG_Y_RTOS+2, mixerStack.available(), UNSIGN|LEFT|TINSIZE); + lcdDrawNumber(lcdLastRightPos+1, MENU_DEBUG_Y_RTOS, mixerStack.available(), UNSIGN|LEFT); lcdDrawText(lcdLastRightPos, MENU_DEBUG_Y_RTOS, "/"); - lcdDrawNumber(lcdLastRightPos, MENU_DEBUG_Y_RTOS+2, audioStack.available(), UNSIGN|LEFT|TINSIZE); -#endif - -#if !defined(CPUARM) + lcdDrawNumber(lcdLastRightPos+1, MENU_DEBUG_Y_RTOS, audioStack.available(), UNSIGN|LEFT); +#else lcdDrawTextAlignedLeft(1*FH, STR_TMR1LATMAXUS); lcdDraw8bitsNumber(MENU_DEBUG_COL1_OFS , 1*FH, g_tmr1Latency_max/2 ); lcdDrawTextAlignedLeft(2*FH, STR_TMR1LATMINUS); @@ -199,3 +275,44 @@ lcdDrawText(4*FW, 7*FH+1, STR_MENUTORESET); lcdInvertLastLine(); } + +#if defined(STM32) +void menuStatisticsDebug2(event_t event) +{ + TITLE(STR_MENUDEBUG); + + switch (event) { + case EVT_KEY_FIRST(KEY_ENTER): + telemetryErrors = 0; + break; + + case EVT_KEY_FIRST(KEY_UP): +#if defined(PCBX7) + case EVT_KEY_BREAK(KEY_PAGE): +#endif + chainMenu(menuStatisticsView); + return; + + case EVT_KEY_FIRST(KEY_DOWN): +#if defined(PCBX7) + case EVT_KEY_LONG(KEY_PAGE): +#endif + killEvents(event); + chainMenu(menuStatisticsDebug); + break; + + case EVT_KEY_FIRST(KEY_EXIT): + chainMenu(menuMainView); + break; + } + + lcdDrawTextAlignedLeft(MENU_DEBUG_ROW1, "Tlm RX Err"); + lcdDrawNumber(MENU_DEBUG_COL1_OFS, MENU_DEBUG_ROW1, telemetryErrors, RIGHT); + + lcdDrawTextAlignedLeft(MENU_DEBUG_ROW2, "BT status"); + lcdDrawNumber(MENU_DEBUG_COL1_OFS, MENU_DEBUG_ROW2, btChipPresent, RIGHT); + + lcdDrawText(4*FW, 7*FH+1, STR_MENUTORESET); + lcdInvertLastLine(); +} +#endif diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/128x64/view_telemetry.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/128x64/view_telemetry.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/128x64/view_telemetry.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/128x64/view_telemetry.cpp 2017-11-10 17:23:25.000000000 +0000 @@ -43,7 +43,7 @@ lcdDrawText(lcdLastLeftPos,STATUS_BAR_Y, "RSSI : ", RIGHT | SMLSIZE); lcdDrawRect(65, 57, 38, 7); uint8_t v = 4*rssi/11; - lcdDrawFilledRect(66+36-v, 58, v, 5, (rssi < getRssiAlarmValue(0)) ? DOTTED : SOLID); + lcdDrawFilledRect(66+36-v, 58, v, 5, (rssi < g_model.rssiAlarms.getWarningRssi()) ? DOTTED : SOLID); #else rssi = min((uint8_t)99, telemetryData.rssi[1].value); lcdDrawTextAlignedLeft(STATUS_BAR_Y, STR_TX); lcdDrawNumber(4*FW+1, STATUS_BAR_Y, rssi, LEADING0, 2); @@ -355,7 +355,12 @@ att |= INVERS|BLINK; } } - drawSourceValue(pos[j+1]-2, (i==3 ? 1+FH+2*FH*i:FH+2*FH*i), field, att); + if(isSensorUnit(1+(field-MIXSRC_FIRST_TELEM)/3, UNIT_DATETIME) && field >= MIXSRC_FIRST_TELEM) { + drawTelemScreenDate(pos[j+1]-36, 6+FH+2*FH*i, field, SMLSIZE|NO_UNIT); + } + else { + drawSourceValue(pos[j+1]-2, (i==3 ? 1+FH+2*FH*i:FH+2*FH*i), field, att); + } } } } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/128x64/widgets.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/128x64/widgets.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/128x64/widgets.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/128x64/widgets.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -258,9 +258,17 @@ } #if defined(CPUARM) || defined(CPUM2560) +const pm_uchar SLEEP_BITMAP[] PROGMEM = { +#include "sleep.lbm" +}; + +#define SLEEP_BITMAP_WIDTH 60 +#define SLEEP_BITMAP_HEIGHT 60 + void drawSleepBitmap() { lcdClear(); - showMessageBox(STR_SHUTDOWN); + lcdDraw1bitBitmap((LCD_W-SLEEP_BITMAP_WIDTH)/2, (LCD_H-SLEEP_BITMAP_HEIGHT)/2, SLEEP_BITMAP, 0); + lcdRefresh(); } #endif diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/gui.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/gui.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/gui.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/gui.h 2017-10-31 16:16:43.000000000 +0000 @@ -34,7 +34,6 @@ #define MENU_HEADER_HEIGHT FH #define MENU_INIT_VPOS 0 -#define BITMAP_BUFFER_SIZE(w, h) (2 + (w) * (((h)+7)/8)*4) #define MODEL_BITMAP_WIDTH 64 #define MODEL_BITMAP_HEIGHT 32 #define MODEL_BITMAP_SIZE BITMAP_BUFFER_SIZE(MODEL_BITMAP_WIDTH, MODEL_BITMAP_HEIGHT) diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/lcd.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/lcd.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/lcd.cpp 2017-04-27 08:57:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/lcd.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -87,7 +87,7 @@ uint8_t lines = (height+7)/8; assert(lines <= 5); - for (int8_t i=0; i= 0x20) { if ( ( c == 46) && ((FONTSIZE(flags) == TINSIZE))) { // '.' handling - if (flags & INVERS) { + if (((flags & BLINK) && BLINK_ON_PHASE) || ((!(flags & BLINK) && (flags & INVERS)))) { lcdDrawSolidVerticalLine(x, y-1, 5); lcdDrawPoint(x, y + 5); } @@ -484,7 +484,7 @@ #if !defined(BOOT) void lcdDrawFilledRect(coord_t x, scoord_t y, coord_t w, coord_t h, uint8_t pat, LcdFlags att) { - for (scoord_t i=y; i= LCD_LINES) return; + uint8_t *p = &displayBuf[line * 4 * LCD_W]; for (coord_t x=0; x> 4) : (*p & 0x0F); } +#if defined(CPUARM) +uint8_t getTextWidth(const char * s, uint8_t len=0, LcdFlags flags=0); +#endif + #endif // _LCD_H_ diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/menus.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/menus.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/menus.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/menus.h 2017-10-31 16:16:43.000000000 +0000 @@ -54,6 +54,7 @@ void menuModelNotes(event_t event); void menuStatisticsView(event_t event); void menuStatisticsDebug(event_t event); +void menuStatisticsDebug2(event_t event); void menuAboutView(event_t event); #if defined(DEBUG_TRACE_BUFFER) void menuTraceBuffer(event_t event); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/model_gvars.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/model_gvars.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/model_gvars.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/model_gvars.cpp 2017-11-15 20:54:40.000000000 +0000 @@ -39,7 +39,7 @@ } if (flags & INVERS) { - if (event == EVT_KEY_LONG(KEY_ENTER)) { + if (event == EVT_KEY_LONG(KEY_ENTER) && flightMode > 0) { v = (v > GVAR_MAX ? 0 : GVAR_MAX+1); storageDirty(EE_MODEL); } @@ -114,7 +114,7 @@ } } -void onGVARSMenu(const char *result) +void onGVARSMenu(const char * result) { int sub = menuVerticalPosition; @@ -165,16 +165,18 @@ LcdFlags attr = ((sub == i && menuHorizontalPosition == j) ? (s_editMode > 0 ? BLINK | INVERS : INVERS) : 0); coord_t x = GVARS_FM_COLUMN(j); + coord_t yval = y; if (v > GVAR_MAX) { attr |= SMLSIZE; } else if (g_model.gvars[i].prec > 0 || abs(v) >= 100) { attr |= TINSIZE | NO_UNIT; + ++yval; } else { attr |= SMLSIZE | NO_UNIT; } - editGVarValue(x, y, event, i, j, attr); + editGVarValue(x, yval, event, i, j, attr); } } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/model_outputs.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/model_outputs.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/model_outputs.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/model_outputs.cpp 2017-11-10 17:23:25.000000000 +0000 @@ -82,9 +82,11 @@ } else if (result == STR_COPY_STICKS_TO_OFS) { copySticksToOffset(ch); + storageDirty(EE_MODEL); } else if (result == STR_COPY_TRIMS_TO_OFS) { copyTrimsToOffset(ch); + storageDirty(EE_MODEL); } } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/model_setup.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/model_setup.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/model_setup.cpp 2017-04-27 08:57:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/model_setup.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -78,18 +78,20 @@ ITEM_MODEL_EXTERNAL_MODULE_MODE, #if defined (MULTIMODULE) ITEM_MODEL_EXTERNAL_MODULE_STATUS, + ITEM_MODEL_EXTERNAL_MODULE_SYNCSTATUS, #endif ITEM_MODEL_EXTERNAL_MODULE_CHANNELS, ITEM_MODEL_EXTERNAL_MODULE_BIND, ITEM_MODEL_EXTERNAL_MODULE_FAILSAFE, + ITEM_MODEL_EXTERNAL_MODULE_OPTIONS, #if defined(MULTIMODULE) ITEM_MODEL_EXTERNAL_MODULE_AUTOBIND, - ITEM_MODEL_EXTERNAL_MODULE_LOWPOWER, #endif + ITEM_MODEL_EXTERNAL_MODULE_POWER, ITEM_MODEL_TRAINER_LABEL, ITEM_MODEL_TRAINER_MODE, - ITEM_MODEL_TRAINER_CHANNELS, - ITEM_MODEL_TRAINER_SETTINGS, + ITEM_MODEL_TRAINER_LINE1, + ITEM_MODEL_TRAINER_LINE2, ITEM_MODEL_SETUP_MAX }; @@ -101,32 +103,54 @@ #define MODEL_SETUP_RANGE_OFS 7*FW #define MODEL_SETUP_SET_FAILSAFE_OFS 10*FW-2 -#if defined(BINDING_OPTIONS) +#define CURRENT_MODULE_EDITED(k) (k>=ITEM_MODEL_TRAINER_LABEL ? TRAINER_MODULE : (k>=ITEM_MODEL_EXTERNAL_MODULE_LABEL ? EXTERNAL_MODULE : INTERNAL_MODULE)) + void onBindMenu(const char * result) { - if (result == STR_BINDING_1_8_TELEM_ON) { - g_model.moduleData[INTERNAL_MODULE].pxx.receiver_telem_off = false; - g_model.moduleData[INTERNAL_MODULE].pxx.receiver_channel_9_16 = false; + uint8_t moduleIdx = CURRENT_MODULE_EDITED(menuVerticalPosition); + + if (result == STR_BINDING_25MW_CH1_8_TELEM_OFF) { + g_model.moduleData[moduleIdx].pxx.power = R9M_LBT_POWER_25; + g_model.moduleData[moduleIdx].pxx.receiver_telem_off = true; + g_model.moduleData[moduleIdx].pxx.receiver_channel_9_16 = false; + } + else if (result == STR_BINDING_25MW_CH1_8_TELEM_ON) { + g_model.moduleData[moduleIdx].pxx.power = R9M_LBT_POWER_25; + g_model.moduleData[moduleIdx].pxx.receiver_telem_off = false; + g_model.moduleData[moduleIdx].pxx.receiver_channel_9_16 = false; + } + else if (result == STR_BINDING_500MW_CH1_8_TELEM_OFF) { + g_model.moduleData[moduleIdx].pxx.power = R9M_LBT_POWER_500; + g_model.moduleData[moduleIdx].pxx.receiver_telem_off = true; + g_model.moduleData[moduleIdx].pxx.receiver_channel_9_16 = false; + } + else if (result == STR_BINDING_500MW_CH9_16_TELEM_OFF) { + g_model.moduleData[moduleIdx].pxx.power = R9M_LBT_POWER_500; + g_model.moduleData[moduleIdx].pxx.receiver_telem_off = true; + g_model.moduleData[moduleIdx].pxx.receiver_channel_9_16 = true; + } + else if (result == STR_BINDING_1_8_TELEM_ON) { + g_model.moduleData[moduleIdx].pxx.receiver_telem_off = false; + g_model.moduleData[moduleIdx].pxx.receiver_channel_9_16 = false; } else if (result == STR_BINDING_1_8_TELEM_OFF) { - g_model.moduleData[INTERNAL_MODULE].pxx.receiver_telem_off = true; - g_model.moduleData[INTERNAL_MODULE].pxx.receiver_channel_9_16 = false; + g_model.moduleData[moduleIdx].pxx.receiver_telem_off = true; + g_model.moduleData[moduleIdx].pxx.receiver_channel_9_16 = false; } else if (result == STR_BINDING_9_16_TELEM_ON) { - g_model.moduleData[INTERNAL_MODULE].pxx.receiver_telem_off = false; - g_model.moduleData[INTERNAL_MODULE].pxx.receiver_channel_9_16 = true; + g_model.moduleData[moduleIdx].pxx.receiver_telem_off = false; + g_model.moduleData[moduleIdx].pxx.receiver_channel_9_16 = true; } else if (result == STR_BINDING_9_16_TELEM_OFF) { - g_model.moduleData[INTERNAL_MODULE].pxx.receiver_telem_off = true; - g_model.moduleData[INTERNAL_MODULE].pxx.receiver_channel_9_16 = true; + g_model.moduleData[moduleIdx].pxx.receiver_telem_off = true; + g_model.moduleData[moduleIdx].pxx.receiver_channel_9_16 = true; } else { return; } - moduleFlag[INTERNAL_MODULE] = MODULE_BIND; + moduleFlag[moduleIdx] = MODULE_BIND; } -#endif void copySelection(char * dst, const char * src, uint8_t size) { @@ -217,8 +241,6 @@ } } -#define CURRENT_MODULE_EDITED(k) (k>=ITEM_MODEL_TRAINER_LABEL ? TRAINER_MODULE : (k>=ITEM_MODEL_EXTERNAL_MODULE_LABEL ? EXTERNAL_MODULE : INTERNAL_MODULE)) - int getSwitchWarningsCount() { int count = 0; @@ -230,23 +252,28 @@ return count; } +#define IF_INTERNAL_MODULE_ON(x) (IS_INTERNAL_MODULE_ENABLED() ? (uint8_t)(x) : HIDDEN_ROW) #if defined(TARANIS_INTERNAL_PPM) - #define IF_INTERNAL_MODULE_ON(x) (g_model.moduleData[INTERNAL_MODULE].type == MODULE_TYPE_NONE ? HIDDEN_ROW : (uint8_t)(x)) #define INTERNAL_MODULE_MODE_ROWS (IS_MODULE_XJT(INTERNAL_MODULE) ? (uint8_t)1 : (uint8_t)0) // Module type + RF protocols #else - #define IF_INTERNAL_MODULE_ON(x) (g_model.moduleData[INTERNAL_MODULE].rfProtocol == RF_PROTO_OFF ? HIDDEN_ROW : (uint8_t)(x)) #define INTERNAL_MODULE_MODE_ROWS 0 // (OFF / RF protocols) #endif -#define IF_EXTERNAL_MODULE_ON(x) (g_model.moduleData[EXTERNAL_MODULE].type == MODULE_TYPE_NONE ? HIDDEN_ROW : (uint8_t)(x)) -#define IF_EXTERNAL_MODULE_XJT(x) (IS_MODULE_XJT(EXTERNAL_MODULE) ? (uint8_t)x : HIDDEN_ROW) +#define IF_EXTERNAL_MODULE_ON(x) (IS_EXTERNAL_MODULE_ENABLED() ? (uint8_t)(x) : HIDDEN_ROW) #define INTERNAL_MODULE_CHANNELS_ROWS IF_INTERNAL_MODULE_ON(1) -#define TRAINER_CHANNELS_ROWS() IF_TRAINER_ON(1) -#define PORT_CHANNELS_ROWS(x) (x==INTERNAL_MODULE ? INTERNAL_MODULE_CHANNELS_ROWS : (x==EXTERNAL_MODULE ? EXTERNAL_MODULE_CHANNELS_ROWS : TRAINER_CHANNELS_ROWS())) +#define PORT_CHANNELS_ROWS(x) (x==INTERNAL_MODULE ? INTERNAL_MODULE_CHANNELS_ROWS : (x==EXTERNAL_MODULE ? EXTERNAL_MODULE_CHANNELS_ROWS : 1)) +#if defined(BLUETOOTH) && defined(USEHORUSBT) + #define TRAINER_LINE1_BLUETOOTH_M_ROWS ((bluetoothDistantAddr[0] == 0 || bluetoothState == BLUETOOTH_STATE_CONNECTED) ? (uint8_t)0 : (uint8_t)1) + #define TRAINER_LINE1_ROWS (g_model.trainerMode == TRAINER_MODE_SLAVE ? (uint8_t)1 : (g_model.trainerMode == TRAINER_MODE_MASTER_BLUETOOTH ? TRAINER_LINE1_BLUETOOTH_M_ROWS : (g_model.trainerMode == TRAINER_MODE_SLAVE_BLUETOOTH ? (uint8_t)1 : HIDDEN_ROW))) + #define TRAINER_LINE2_ROWS (g_model.trainerMode == TRAINER_MODE_SLAVE ? (uint8_t)2 : HIDDEN_ROW) +#else + #define TRAINER_LINE1_ROWS (g_model.trainerMode == TRAINER_MODE_SLAVE ? (uint8_t)1 : HIDDEN_ROW) + #define TRAINER_LINE2_ROWS (g_model.trainerMode == TRAINER_MODE_SLAVE ? (uint8_t)2 : HIDDEN_ROW) +#endif #define TIMER_ROWS(x) 2|NAVIGATION_LINE_BY_LINE, 0, 0, 0, g_model.timers[x].countdownBeep != COUNTDOWN_SILENT ? (uint8_t) 1 : (uint8_t)0 -#define EXTERNAL_MODULE_MODE_ROWS (IS_MODULE_XJT(EXTERNAL_MODULE) || IS_MODULE_DSM2(EXTERNAL_MODULE)) ? (uint8_t)1 : IS_MODULE_MULTIMODULE(EXTERNAL_MODULE) ? MULTIMODULE_MODE_ROWS(EXTERNAL_MODULE) : (uint8_t)0 +#define EXTERNAL_MODULE_MODE_ROWS (IS_MODULE_PXX(EXTERNAL_MODULE) || IS_MODULE_DSM2(EXTERNAL_MODULE)) ? (uint8_t)1 : IS_MODULE_MULTIMODULE(EXTERNAL_MODULE) ? MULTIMODULE_MODE_ROWS(EXTERNAL_MODULE) : (uint8_t)0 #if TIMERS == 1 #define TIMERS_ROWS TIMER_ROWS(0) @@ -281,11 +308,11 @@ IF_INTERNAL_MODULE_ON((IS_MODULE_XJT(INTERNAL_MODULE)) ? FAILSAFE_ROWS(INTERNAL_MODULE) : HIDDEN_ROW), LABEL(ExternalModule), EXTERNAL_MODULE_MODE_ROWS, - MULTIMODULE_STATUS_ROW + MULTIMODULE_STATUS_ROWS EXTERNAL_MODULE_CHANNELS_ROWS, (IS_MODULE_XJT(EXTERNAL_MODULE) && !HAS_RF_PROTOCOL_FAILSAFE(g_model.moduleData[EXTERNAL_MODULE].rfProtocol)) ? (uint8_t)1 : (IS_MODULE_PPM(EXTERNAL_MODULE) || IS_MODULE_XJT(EXTERNAL_MODULE) || IS_MODULE_DSM2(EXTERNAL_MODULE) || IS_MODULE_MULTIMODULE(EXTERNAL_MODULE)) ? (uint8_t)2 : HIDDEN_ROW, - FAILSAFE_ROWS(EXTERNAL_MODULE), MULTIMODULE_MODULE_ROWS - LABEL(Trainer), 0, TRAINER_CHANNELS_ROWS(), IF_TRAINER_ON(2)}); + FAILSAFE_ROWS(EXTERNAL_MODULE), EXTERNAL_MODULE_OPTION_ROW, MULTIMODULE_MODULE_ROWS EXTERNAL_MODULE_POWER_ROW, + LABEL(Trainer), 0, TRAINER_LINE1_ROWS, TRAINER_LINE2_ROWS}); #else MENU_TAB({ 0, 0, TIMERS_ROWS, TOPLCD_ROWS 0, 1, 0, 0, LABEL(Throttle), 0, 0, 0, @@ -297,11 +324,14 @@ IF_INTERNAL_MODULE_ON(FAILSAFE_ROWS(INTERNAL_MODULE)), LABEL(ExternalModule), EXTERNAL_MODULE_MODE_ROWS, - MULTIMODULE_STATUS_ROW + MULTIMODULE_STATUS_ROWS EXTERNAL_MODULE_CHANNELS_ROWS, - (IS_MODULE_XJT(EXTERNAL_MODULE) && !HAS_RF_PROTOCOL_FAILSAFE(g_model.moduleData[EXTERNAL_MODULE].rfProtocol)) ? (uint8_t)1 : (IS_MODULE_PPM(EXTERNAL_MODULE) || IS_MODULE_XJT(EXTERNAL_MODULE) || IS_MODULE_DSM2(EXTERNAL_MODULE) || IS_MODULE_MULTIMODULE(EXTERNAL_MODULE)) ? (uint8_t)2 : HIDDEN_ROW, - FAILSAFE_ROWS(EXTERNAL_MODULE), MULTIMODULE_MODULE_ROWS - LABEL(Trainer), 0, TRAINER_CHANNELS_ROWS(), IF_TRAINER_ON(2)}); + ((IS_MODULE_XJT(EXTERNAL_MODULE) && !HAS_RF_PROTOCOL_FAILSAFE(g_model.moduleData[EXTERNAL_MODULE].rfProtocol)) || IS_MODULE_SBUS(EXTERNAL_MODULE)) ? (uint8_t)1 : (IS_MODULE_PPM(EXTERNAL_MODULE) || IS_MODULE_PXX(EXTERNAL_MODULE) || IS_MODULE_DSM2(EXTERNAL_MODULE) || IS_MODULE_MULTIMODULE(EXTERNAL_MODULE)) ? (uint8_t)2 : HIDDEN_ROW, + FAILSAFE_ROWS(EXTERNAL_MODULE), + EXTERNAL_MODULE_OPTION_ROW, + MULTIMODULE_MODULE_ROWS + EXTERNAL_MODULE_POWER_ROW, + LABEL(Trainer), 0, TRAINER_LINE1_ROWS, TRAINER_LINE2_ROWS}); #endif MENU_CHECK(STR_MENUSETUP, menuTabModel, MENU_MODEL_SETUP, ITEM_MODEL_SETUP_MAX); @@ -697,11 +727,14 @@ lcdDrawTextAlignedLeft(y, STR_MODE); lcdDrawTextAtIndex(MODEL_SETUP_2ND_COLUMN, y, STR_XJT_PROTOCOLS, 1+g_model.moduleData[0].rfProtocol, attr); if (attr) { - g_model.moduleData[INTERNAL_MODULE].rfProtocol = checkIncDec(event, g_model.moduleData[INTERNAL_MODULE].rfProtocol, RF_PROTO_OFF, RF_PROTO_LAST, EE_MODEL, isRfProtocolAvailable); + g_model.moduleData[INTERNAL_MODULE].rfProtocol = checkIncDec(event, g_model.moduleData[INTERNAL_MODULE].rfProtocol, -1, RF_PROTO_LAST, EE_MODEL, isRfProtocolAvailable); + if (checkIncDec_Ret) { - g_model.moduleData[0].type = MODULE_TYPE_XJT; - g_model.moduleData[0].channelsStart = 0; - g_model.moduleData[0].channelsCount = DEFAULT_CHANNELS(INTERNAL_MODULE); + g_model.moduleData[INTERNAL_MODULE].type = MODULE_TYPE_XJT; + g_model.moduleData[INTERNAL_MODULE].channelsStart = 0; + g_model.moduleData[INTERNAL_MODULE].channelsCount = DEFAULT_CHANNELS(INTERNAL_MODULE); + if (g_model.moduleData[INTERNAL_MODULE].rfProtocol == RF_PROTO_OFF) + g_model.moduleData[INTERNAL_MODULE].type = MODULE_TYPE_NONE; } } break; @@ -709,7 +742,15 @@ case ITEM_MODEL_TRAINER_MODE: lcdDrawTextAlignedLeft(y, STR_MODE); lcdDrawTextAtIndex(MODEL_SETUP_2ND_COLUMN, y, STR_VTRAINERMODES, g_model.trainerMode, attr); - if (attr) g_model.trainerMode = checkIncDec(event, g_model.trainerMode, 0, HAS_WIRELESS_TRAINER_HARDWARE() ? TRAINER_MODE_MASTER_BATTERY_COMPARTMENT : TRAINER_MODE_MASTER_CPPM_EXTERNAL_MODULE, EE_MODEL, isTrainerModeAvailable); + if (attr) { + g_model.trainerMode = checkIncDec(event, g_model.trainerMode, 0, TRAINER_MODE_MAX(), EE_MODEL, isTrainerModeAvailable); + } +#if defined(BLUETOOTH) && defined(USEHORUSBT) + if (attr && checkIncDec_Ret) { + bluetoothState = BLUETOOTH_STATE_OFF; + bluetoothDistantAddr[0] = 0; + } +#endif break; case ITEM_MODEL_EXTERNAL_MODULE_LABEL: @@ -723,6 +764,8 @@ lcdDrawTextAtIndex(MODEL_SETUP_3RD_COLUMN, y, STR_XJT_PROTOCOLS, 1+g_model.moduleData[EXTERNAL_MODULE].rfProtocol, menuHorizontalPosition==1 ? attr : 0); else if (IS_MODULE_DSM2(EXTERNAL_MODULE)) lcdDrawTextAtIndex(MODEL_SETUP_3RD_COLUMN, y, STR_DSM_PROTOCOLS, g_model.moduleData[EXTERNAL_MODULE].rfProtocol, menuHorizontalPosition==1 ? attr : 0); + else if (IS_MODULE_R9M(EXTERNAL_MODULE)) + lcdDrawTextAtIndex(MODEL_SETUP_3RD_COLUMN, y, STR_R9M_MODES, g_model.moduleData[EXTERNAL_MODULE].subType, (menuHorizontalPosition==1 ? attr : 0)); #if defined(MULTIMODULE) else if (IS_MODULE_MULTIMODULE(EXTERNAL_MODULE)) { uint8_t multi_rfProto = g_model.moduleData[EXTERNAL_MODULE].getMultiProtocol(false); @@ -750,11 +793,15 @@ g_model.moduleData[EXTERNAL_MODULE].rfProtocol = 0; g_model.moduleData[EXTERNAL_MODULE].channelsStart = 0; g_model.moduleData[EXTERNAL_MODULE].channelsCount = DEFAULT_CHANNELS(EXTERNAL_MODULE); + if (IS_MODULE_SBUS(EXTERNAL_MODULE)) + g_model.moduleData[EXTERNAL_MODULE].sbus.refreshRate = -31; } break; case 1: if (IS_MODULE_DSM2(EXTERNAL_MODULE)) CHECK_INCDEC_MODELVAR(event, g_model.moduleData[EXTERNAL_MODULE].rfProtocol, DSM2_PROTO_LP45, DSM2_PROTO_DSMX); + else if (IS_MODULE_R9M(EXTERNAL_MODULE)) + CHECK_INCDEC_MODELVAR(event, g_model.moduleData[EXTERNAL_MODULE].subType, MODULE_SUBTYPE_R9M_FCC, MODULE_SUBTYPE_R9M_LBT); #if defined(MULTIMODULE) else if (IS_MODULE_MULTIMODULE(EXTERNAL_MODULE)) { int multiRfProto = g_model.moduleData[EXTERNAL_MODULE].multi.customProto == 1 ? MM_RF_PROTO_CUSTOM : g_model.moduleData[EXTERNAL_MODULE].getMultiProtocol(false); @@ -767,7 +814,8 @@ // Sensible default for DSM2 (same as for ppm): 7ch@22ms + Autodetect settings enabled if (g_model.moduleData[EXTERNAL_MODULE].getMultiProtocol(true) == MM_RF_PROTO_DSM2) { g_model.moduleData[EXTERNAL_MODULE].multi.autoBindMode = 1; - } else { + } + else { g_model.moduleData[EXTERNAL_MODULE].multi.autoBindMode = 0; } g_model.moduleData[EXTERNAL_MODULE].multi.optionValue = 0; @@ -787,8 +835,9 @@ if (g_model.moduleData[EXTERNAL_MODULE].multi.customProto) { g_model.moduleData[EXTERNAL_MODULE].setMultiProtocol(checkIncDec(event, g_model.moduleData[EXTERNAL_MODULE].getMultiProtocol(false), 0, 63, EE_MODEL)); break; - } else { - const mm_protocol_definition* pdef = getMultiProtocolDefinition(g_model.moduleData[EXTERNAL_MODULE].getMultiProtocol(false)); + } + else { + const mm_protocol_definition * pdef = getMultiProtocolDefinition(g_model.moduleData[EXTERNAL_MODULE].getMultiProtocol(false)); if (pdef->maxSubtype > 0) CHECK_INCDEC_MODELVAR(event, g_model.moduleData[EXTERNAL_MODULE].subType, 0, pdef->maxSubtype); } @@ -802,13 +851,56 @@ } break; - case ITEM_MODEL_TRAINER_LABEL: - lcdDrawTextAlignedLeft(y, STR_TRAINER); - break; + case ITEM_MODEL_TRAINER_LABEL: + lcdDrawTextAlignedLeft(y, STR_TRAINER); + break; +#if defined(BLUETOOTH) && defined(USEHORUSBT) + case ITEM_MODEL_TRAINER_LINE1: + if (g_model.trainerMode == TRAINER_MODE_MASTER_BLUETOOTH) { + if (attr) { + s_editMode = 0; + } + if (bluetoothDistantAddr[0]) { + lcdDrawText(INDENT_WIDTH, y+1, bluetoothDistantAddr, TINSIZE); + if (bluetoothState != BLUETOOTH_STATE_CONNECTED) { + lcdDrawText(MODEL_SETUP_2ND_COLUMN, y, BUTTON("Bind"), menuHorizontalPosition == 0 ? attr : 0); + lcdDrawText(MODEL_SETUP_2ND_COLUMN+5*FW, y, BUTTON("Clear"), menuHorizontalPosition == 1 ? attr : 0); + } + else { + lcdDrawText(MODEL_SETUP_2ND_COLUMN, y, BUTTON("Clear"), attr); + } + if (attr && event == EVT_KEY_FIRST(KEY_ENTER)) { + if (bluetoothState == BLUETOOTH_STATE_CONNECTED || menuHorizontalPosition == 1) { + bluetoothState = BLUETOOTH_STATE_OFF; + bluetoothDistantAddr[0] = 0; + } + else { + bluetoothState = BLUETOOTH_STATE_BIND_REQUESTED; + } + } + } + else { + lcdDrawText(INDENT_WIDTH, y, "---"); + if (bluetoothState < BLUETOOTH_STATE_IDLE) + lcdDrawText(MODEL_SETUP_2ND_COLUMN, y, BUTTON("Init"), attr); + else + lcdDrawText(MODEL_SETUP_2ND_COLUMN, y, BUTTON("Discover"), attr); + if (attr && event == EVT_KEY_FIRST(KEY_ENTER)) { + if (bluetoothState < BLUETOOTH_STATE_IDLE) + bluetoothState = BLUETOOTH_STATE_OFF; + else + bluetoothState = BLUETOOTH_STATE_DISCOVER_REQUESTED; + } + } + break; + } + // no break +#else + case ITEM_MODEL_TRAINER_LINE1: +#endif case ITEM_MODEL_INTERNAL_MODULE_CHANNELS: case ITEM_MODEL_EXTERNAL_MODULE_CHANNELS: - case ITEM_MODEL_TRAINER_CHANNELS: { uint8_t moduleIdx = CURRENT_MODULE_EDITED(k); ModuleData & moduleData = g_model.moduleData[moduleIdx]; @@ -818,7 +910,7 @@ lcdDrawNumber(lcdLastRightPos, y, moduleData.channelsStart+1, LEFT | (menuHorizontalPosition==0 ? attr : 0)); lcdDrawChar(lcdLastRightPos, y, '-'); lcdDrawNumber(lcdLastRightPos + FW+1, y, moduleData.channelsStart+NUM_CHANNELS(moduleIdx), LEFT | (menuHorizontalPosition==1 ? attr : 0)); - if (IS_MODULE_XJT(moduleIdx) && g_model.moduleData[moduleIdx].rfProtocol== RF_PROTO_X16) { + if (IS_R9M_OR_XJTD16(moduleIdx)) { if (NUM_CHANNELS(moduleIdx) > 8) lcdDrawText(lcdLastRightPos+5, y, "(18ms)"); else @@ -832,11 +924,11 @@ case 1: CHECK_INCDEC_MODELVAR(event, moduleData.channelsCount, -4, min(MAX_CHANNELS(moduleIdx), 32-8-moduleData.channelsStart)); #if defined(TARANIS_INTERNAL_PPM) - if ((k == ITEM_MODEL_EXTERNAL_MODULE_CHANNELS && g_model.moduleData[EXTERNAL_MODULE].type == MODULE_TYPE_PPM) || (k == ITEM_MODEL_INTERNAL_MODULE_CHANNELS && g_model.moduleData[INTERNAL_MODULE].type == MODULE_TYPE_PPM) || (k == ITEM_MODEL_TRAINER_CHANNELS)) { + if ((k == ITEM_MODEL_EXTERNAL_MODULE_CHANNELS && g_model.moduleData[EXTERNAL_MODULE].type == MODULE_TYPE_PPM) || (k == ITEM_MODEL_INTERNAL_MODULE_CHANNELS && g_model.moduleData[INTERNAL_MODULE].type == MODULE_TYPE_PPM) || (k == ITEM_MODEL_TRAINER_LINE1)) { SET_DEFAULT_PPM_FRAME_LENGTH(moduleIdx); } #else - if ((k == ITEM_MODEL_EXTERNAL_MODULE_CHANNELS && g_model.moduleData[EXTERNAL_MODULE].type == MODULE_TYPE_PPM) || (k == ITEM_MODEL_TRAINER_CHANNELS)) { + if ((k == ITEM_MODEL_EXTERNAL_MODULE_CHANNELS && g_model.moduleData[EXTERNAL_MODULE].type == MODULE_TYPE_PPM) || (k == ITEM_MODEL_TRAINER_LINE1)) { SET_DEFAULT_PPM_FRAME_LENGTH(moduleIdx); } #endif @@ -849,7 +941,7 @@ case ITEM_MODEL_INTERNAL_MODULE_BIND: case ITEM_MODEL_EXTERNAL_MODULE_BIND: - case ITEM_MODEL_TRAINER_SETTINGS: + case ITEM_MODEL_TRAINER_LINE2: { uint8_t moduleIdx = CURRENT_MODULE_EDITED(k); ModuleData & moduleData = g_model.moduleData[moduleIdx]; @@ -875,6 +967,23 @@ } } } + else if (IS_MODULE_SBUS(moduleIdx)) { + lcdDrawTextAlignedLeft(y, STR_REFRESHRATE); + lcdDrawNumber(MODEL_SETUP_2ND_COLUMN, y, (int16_t)moduleData.ppm.frameLength*5 + 225, (menuHorizontalPosition<=0 ? attr : 0) | PREC1|LEFT); + lcdDrawText(lcdLastRightPos, y, STR_MS); + lcdDrawText(MODEL_SETUP_3RD_COLUMN, y, moduleData.sbus.noninverted ? "not inverted" : "normal", (CURSOR_ON_LINE() || menuHorizontalPosition==1) ? attr : 0); + + if (attr && s_editMode>0) { + switch (menuHorizontalPosition) { + case 0: + CHECK_INCDEC_MODELVAR(event, moduleData.ppm.frameLength, -33, 35); + break; + case 1: + CHECK_INCDEC_MODELVAR_ZERO(event, moduleData.sbus.noninverted, 1); + break; + } + } + } else { horzpos_t l_posHorz = menuHorizontalPosition; coord_t xOffsetBind = MODEL_SETUP_BIND_OFS; @@ -886,12 +995,12 @@ else { lcdDrawTextAlignedLeft(y, STR_RECEIVER_NUM); } - if (IS_MODULE_XJT(moduleIdx) || IS_MODULE_DSM2(moduleIdx) || IS_MODULE_MULTIMODULE(moduleIdx)) { - if (xOffsetBind) lcdDrawNumber(MODEL_SETUP_2ND_COLUMN, y, g_model.header.modelId[moduleIdx], (l_posHorz==0 ? attr : 0) | LEADING0|LEFT, 2); + if (IS_MODULE_PXX(moduleIdx) || IS_MODULE_DSM2(moduleIdx) || IS_MODULE_MULTIMODULE(moduleIdx)) { + if (xOffsetBind) + lcdDrawNumber(MODEL_SETUP_2ND_COLUMN, y, g_model.header.modelId[moduleIdx], (l_posHorz==0 ? attr : 0) | LEADING0|LEFT, 2); if (attr && l_posHorz==0) { if (s_editMode>0) { CHECK_INCDEC_MODELVAR_ZERO(event, g_model.header.modelId[moduleIdx], MAX_RX_NUM(moduleIdx)); - if (checkIncDec_Ret) { modelHeaders[g_eeGeneral.currModel].modelId[moduleIdx] = g_model.header.modelId[moduleIdx]; } @@ -906,29 +1015,42 @@ #if defined(MULTIMODULE) if (multiBindStatus == MULTI_BIND_FINISHED) { multiBindStatus = MULTI_NORMAL_OPERATION; - s_editMode=0; + s_editMode = 0; } #endif -#if defined(BINDING_OPTIONS) if (attr && l_posHorz>0) { - if(s_editMode>0) { + if (s_editMode>0) { if (l_posHorz == 1) { - if (IS_MODULE_XJT(moduleIdx) && g_model.moduleData[moduleIdx].rfProtocol== RF_PROTO_X16 && s_current_protocol[INTERNAL_MODULE] == PROTO_PXX) { - if(event==EVT_KEY_BREAK(KEY_ENTER)) { - POPUP_MENU_ADD_ITEM(STR_BINDING_1_8_TELEM_ON); - POPUP_MENU_ADD_ITEM(STR_BINDING_1_8_TELEM_OFF); - POPUP_MENU_ADD_ITEM(STR_BINDING_9_16_TELEM_ON); - POPUP_MENU_ADD_ITEM(STR_BINDING_9_16_TELEM_OFF); - POPUP_MENU_SELECT_ITEM(g_model.moduleData[INTERNAL_MODULE].pxx.receiver_telem_off + (g_model.moduleData[INTERNAL_MODULE].pxx.receiver_channel_9_16 << 1)); + if (IS_MODULE_R9M(moduleIdx) || (IS_MODULE_XJT(moduleIdx) && g_model.moduleData[moduleIdx].rfProtocol== RF_PROTO_X16)) { + if (event == EVT_KEY_BREAK(KEY_ENTER)) { + uint8_t default_selection; + if (IS_MODULE_R9M_LBT(moduleIdx)) { + if (!IS_TELEMETRY_INTERNAL_MODULE()) + POPUP_MENU_ADD_ITEM(STR_BINDING_25MW_CH1_8_TELEM_ON); + POPUP_MENU_ADD_ITEM(STR_BINDING_25MW_CH1_8_TELEM_OFF); + POPUP_MENU_ADD_ITEM(STR_BINDING_500MW_CH1_8_TELEM_OFF); + POPUP_MENU_ADD_ITEM(STR_BINDING_500MW_CH9_16_TELEM_OFF); + default_selection = 1; + } + else { + if (!(IS_TELEMETRY_INTERNAL_MODULE() && moduleIdx == EXTERNAL_MODULE)) + POPUP_MENU_ADD_ITEM(STR_BINDING_1_8_TELEM_ON); + POPUP_MENU_ADD_ITEM(STR_BINDING_1_8_TELEM_OFF); + if (!(IS_TELEMETRY_INTERNAL_MODULE() && moduleIdx == EXTERNAL_MODULE)) + POPUP_MENU_ADD_ITEM(STR_BINDING_9_16_TELEM_ON); + POPUP_MENU_ADD_ITEM(STR_BINDING_9_16_TELEM_OFF); + default_selection = g_model.moduleData[moduleIdx].pxx.receiver_telem_off + (g_model.moduleData[moduleIdx].pxx.receiver_channel_9_16 << 1); + } + POPUP_MENU_SELECT_ITEM(default_selection); POPUP_MENU_START(onBindMenu); continue; } - if (moduleFlag[INTERNAL_MODULE] == MODULE_BIND) { + if (moduleFlag[moduleIdx] == MODULE_BIND) { newFlag = MODULE_BIND; } else { if (!popupMenuNoItems) { - s_editMode=0; // this is when popup is exited before a choice is made + s_editMode = 0; // this is when popup is exited before a choice is made } } } @@ -939,13 +1061,6 @@ else if (l_posHorz == 2) { newFlag = MODULE_RANGECHECK; } -#else - if (attr && l_posHorz>0 && s_editMode>0) { - if (l_posHorz == 1) - newFlag = MODULE_BIND; - else if (l_posHorz == 2) { - newFlag = MODULE_RANGECHECK; -#endif } } moduleFlag[moduleIdx] = newFlag; @@ -962,70 +1077,118 @@ case ITEM_MODEL_EXTERNAL_MODULE_FAILSAFE: { uint8_t moduleIdx = CURRENT_MODULE_EDITED(k); - if (IS_MODULE_XJT(moduleIdx)) { - ModuleData & moduleData = g_model.moduleData[moduleIdx]; - lcdDrawTextAlignedLeft(y, STR_FAILSAFE); - lcdDrawTextAtIndex(MODEL_SETUP_2ND_COLUMN, y, STR_VFAILSAFE, moduleData.failsafeMode, menuHorizontalPosition==0 ? attr : 0); - if (moduleData.failsafeMode == FAILSAFE_CUSTOM) lcdDrawText(MODEL_SETUP_2ND_COLUMN + MODEL_SETUP_SET_FAILSAFE_OFS, y, STR_SET, menuHorizontalPosition==1 ? attr : 0); - if (attr) { - if (moduleData.failsafeMode != FAILSAFE_CUSTOM) { - menuHorizontalPosition = 0; - } - if (menuHorizontalPosition == 0) { - if (s_editMode > 0) { - CHECK_INCDEC_MODELVAR_ZERO(event, moduleData.failsafeMode, FAILSAFE_LAST); - if (checkIncDec_Ret) SEND_FAILSAFE_NOW(moduleIdx); - } - } - else if (menuHorizontalPosition == 1) { - s_editMode = 0; - if (moduleData.failsafeMode==FAILSAFE_CUSTOM && event==EVT_KEY_FIRST(KEY_ENTER)) { - g_moduleIdx = moduleIdx; - pushMenu(menuModelFailsafe); - } - } - else { - lcdDrawFilledRect(MODEL_SETUP_2ND_COLUMN, y, LCD_W-MODEL_SETUP_2ND_COLUMN-MENUS_SCROLLBAR_WIDTH, 8); + ModuleData & moduleData = g_model.moduleData[moduleIdx]; + lcdDrawTextAlignedLeft(y, STR_FAILSAFE); + lcdDrawTextAtIndex(MODEL_SETUP_2ND_COLUMN, y, STR_VFAILSAFE, moduleData.failsafeMode, menuHorizontalPosition==0 ? attr : 0); + if (moduleData.failsafeMode == FAILSAFE_CUSTOM) lcdDrawText(MODEL_SETUP_2ND_COLUMN + MODEL_SETUP_SET_FAILSAFE_OFS, y, STR_SET, menuHorizontalPosition==1 ? attr : 0); + if (attr) { + if (moduleData.failsafeMode != FAILSAFE_CUSTOM) { + menuHorizontalPosition = 0; + } + if (menuHorizontalPosition == 0) { + if (s_editMode > 0) { + CHECK_INCDEC_MODELVAR_ZERO(event, moduleData.failsafeMode, FAILSAFE_LAST); + if (checkIncDec_Ret) SEND_FAILSAFE_NOW(moduleIdx); } } - } -#if defined(MULTIMODULE) - else if (IS_MODULE_MULTIMODULE(moduleIdx)) { - int optionValue = g_model.moduleData[moduleIdx].multi.optionValue; - - const uint8_t multi_proto = g_model.moduleData[EXTERNAL_MODULE].getMultiProtocol(true); - const mm_protocol_definition* pdef = getMultiProtocolDefinition(multi_proto); - if (pdef->optionsstr) - lcdDrawTextAlignedLeft(y, pdef->optionsstr); - - if (multi_proto == MM_RF_PROTO_FS_AFHDS2A) - optionValue = 50 + 5 * optionValue; - - lcdDrawNumber(MODEL_SETUP_2ND_COLUMN, y, optionValue, LEFT | attr); - if (attr) { - if (multi_proto == MM_RF_PROTO_FS_AFHDS2A) { - CHECK_INCDEC_MODELVAR(event, g_model.moduleData[moduleIdx].multi.optionValue, 0, 70); - } else if (multi_proto == MM_RF_PROTO_OLRS) { - CHECK_INCDEC_MODELVAR(event, g_model.moduleData[moduleIdx].multi.optionValue, -1, 7); - } else { - CHECK_INCDEC_MODELVAR(event, g_model.moduleData[moduleIdx].multi.optionValue, -128, 127); + else if (menuHorizontalPosition == 1) { + s_editMode = 0; + if (moduleData.failsafeMode==FAILSAFE_CUSTOM && event==EVT_KEY_FIRST(KEY_ENTER)) { + g_moduleIdx = moduleIdx; + pushMenu(menuModelFailsafe); } } + else { + lcdDrawFilledRect(MODEL_SETUP_2ND_COLUMN, y, LCD_W - MODEL_SETUP_2ND_COLUMN - MENUS_SCROLLBAR_WIDTH, 8); + } } -#endif break; } + break; + + case ITEM_MODEL_EXTERNAL_MODULE_OPTIONS: + { + uint8_t moduleIdx = CURRENT_MODULE_EDITED(k); #if defined(MULTIMODULE) + + if (IS_MODULE_MULTIMODULE(moduleIdx)) { + int optionValue = g_model.moduleData[moduleIdx].multi.optionValue; + + const uint8_t multi_proto = g_model.moduleData[EXTERNAL_MODULE].getMultiProtocol(true); + const mm_protocol_definition *pdef = getMultiProtocolDefinition(multi_proto); + if (pdef->optionsstr) + lcdDrawText(INDENT_WIDTH, y, pdef->optionsstr); + + if (multi_proto == MM_RF_PROTO_FS_AFHDS2A) + optionValue = 50 + 5 * optionValue; + + lcdDrawNumber(MODEL_SETUP_2ND_COLUMN, y, optionValue, LEFT | attr); + if (attr) { + if (multi_proto == MM_RF_PROTO_FS_AFHDS2A) { + CHECK_INCDEC_MODELVAR(event, g_model.moduleData[moduleIdx].multi.optionValue, 0, 70); + } + else if (multi_proto == MM_RF_PROTO_OLRS) { + CHECK_INCDEC_MODELVAR(event, g_model.moduleData[moduleIdx].multi.optionValue, -1, 7); + } + else { + CHECK_INCDEC_MODELVAR(event, g_model.moduleData[moduleIdx].multi.optionValue, -128, 127); + } + } + } +#endif + if (IS_MODULE_R9M_FCC(moduleIdx)) { + if (IS_TELEMETRY_INTERNAL_MODULE()) { + lcdDrawTextAlignedLeft(y, STR_MODULE_TELEMETRY); + lcdDrawText(MODEL_SETUP_2ND_COLUMN, y, STR_DISABLE_INTERNAL); + } + else { + g_model.moduleData[moduleIdx].pxx.sport_out = editCheckBox(g_model.moduleData[EXTERNAL_MODULE].pxx.sport_out, MODEL_SETUP_2ND_COLUMN, y, STR_MODULE_TELEMETRY, attr, event); + } + } + else if (IS_MODULE_R9M_LBT(moduleIdx)) { + if (IS_TELEMETRY_INTERNAL_MODULE()) { + lcdDrawTextAlignedLeft(y, STR_MODULE_TELEMETRY); + lcdDrawText(MODEL_SETUP_2ND_COLUMN, y, STR_DISABLE_INTERNAL); + } + else { + lcdDrawTextAlignedLeft(y, STR_MODULE_TELEMETRY); + lcdDrawText(MODEL_SETUP_2ND_COLUMN, y, STR_BINDING_OPTION); + } + } + else if (IS_MODULE_SBUS(moduleIdx)) { + lcdDrawTextAlignedLeft(y, STR_WARN_BATTVOLTAGE); + putsVolts(lcdLastRightPos, y, getBatteryVoltage(), attr | PREC2 | LEFT); + } + } + break; + + case ITEM_MODEL_EXTERNAL_MODULE_POWER: + { + uint8_t moduleIdx = CURRENT_MODULE_EDITED(k); + if (IS_MODULE_R9M_FCC(moduleIdx)) { + // Power selection is only available on R9M FCC + lcdDrawTextAlignedLeft(y, TR_MULTI_RFPOWER); + lcdDrawTextAtIndex(MODEL_SETUP_2ND_COLUMN, y, STR_R9M_FCC_POWER_VALUES, g_model.moduleData[moduleIdx].pxx.power, LEFT | attr); + if (attr) + CHECK_INCDEC_MODELVAR(event, g_model.moduleData[moduleIdx].pxx.power, 0, R9M_FCC_POWER_MAX); + } +#if defined (MULTIMODULE) + else if (IS_MODULE_MULTIMODULE(moduleIdx)) { + g_model.moduleData[EXTERNAL_MODULE].multi.lowPowerMode = editCheckBox(g_model.moduleData[EXTERNAL_MODULE].multi.lowPowerMode, MODEL_SETUP_2ND_COLUMN, y, STR_MULTI_LOWPOWER, attr, event); + } +#endif + break; + } + +#if defined (MULTIMODULE) case ITEM_MODEL_EXTERNAL_MODULE_AUTOBIND: if (g_model.moduleData[EXTERNAL_MODULE].getMultiProtocol(true) == MM_RF_PROTO_DSM2) g_model.moduleData[EXTERNAL_MODULE].multi.autoBindMode = editCheckBox(g_model.moduleData[EXTERNAL_MODULE].multi.autoBindMode, MODEL_SETUP_2ND_COLUMN, y, STR_MULTI_DSM_AUTODTECT, attr, event); else g_model.moduleData[EXTERNAL_MODULE].multi.autoBindMode = editCheckBox(g_model.moduleData[EXTERNAL_MODULE].multi.autoBindMode, MODEL_SETUP_2ND_COLUMN, y, STR_MULTI_AUTOBIND, attr, event); break; - case ITEM_MODEL_EXTERNAL_MODULE_LOWPOWER: - g_model.moduleData[EXTERNAL_MODULE].multi.lowPowerMode = editCheckBox(g_model.moduleData[EXTERNAL_MODULE].multi.lowPowerMode, MODEL_SETUP_2ND_COLUMN, y, STR_MULTI_LOWPOWER, attr, event); - break; - case ITEM_MODEL_EXTERNAL_MODULE_STATUS: { + case ITEM_MODEL_EXTERNAL_MODULE_STATUS: + { lcdDrawTextAlignedLeft(y, STR_MODULE_STATUS); char statusText[64]; @@ -1033,6 +1196,14 @@ lcdDrawText(MODEL_SETUP_2ND_COLUMN, y, statusText); break; } + case ITEM_MODEL_EXTERNAL_MODULE_SYNCSTATUS: { + lcdDrawTextAlignedLeft(y, STR_MODULE_SYNC); + + char statusText[64]; + multiSyncStatus.getRefreshString(statusText); + lcdDrawText(MODEL_SETUP_2ND_COLUMN, y, statusText); + break; + } #endif } } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/model_special_functions.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/model_special_functions.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/model_special_functions.cpp 2017-04-29 16:57:04.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/model_special_functions.cpp 2017-11-15 20:54:40.000000000 +0000 @@ -174,7 +174,7 @@ drawStringWithIndex(0, y, functions == g_model.customFn ? STR_SF : STR_GF, k+1, (sub==k && menuHorizontalPosition<0) ? INVERS : 0); - CustomFunctionData *cfn = &functions[k]; + CustomFunctionData * cfn = &functions[k]; uint8_t func = CFN_FUNC(cfn); for (uint8_t j=0; j<5; j++) { uint8_t attr = ((sub==k && menuHorizontalPosition==j) ? ((s_editMode>0) ? BLINK|INVERS : INVERS) : 0); @@ -182,7 +182,7 @@ switch (j) { case ITEM_CUSTOM_FUNCTIONS_SWITCH: drawSwitch(MODEL_SPECIAL_FUNC_1ST_COLUMN, y, CFN_SWITCH(cfn), attr | ((functionsContext->activeSwitches & ((MASK_CFN_TYPE)1 << k)) ? BOLD : 0)); - if (active || AUTOSWITCH_ENTER_LONG()) CHECK_INCDEC_SWITCH(event, CFN_SWITCH(cfn), SWSRC_FIRST, functionsContext == &globalFunctionsContext ? SWSRC_TELEMETRY_STREAMING : SWSRC_LAST, eeFlags, isSwitchAvailableInCustomFunctions); + if (active || AUTOSWITCH_ENTER_LONG()) CHECK_INCDEC_SWITCH(event, CFN_SWITCH(cfn), SWSRC_FIRST, SWSRC_LAST, eeFlags, isSwitchAvailableInCustomFunctions); if (func == FUNC_OVERRIDE_CHANNEL && functions != g_model.customFn) { func = CFN_FUNC(cfn) = func+1; } @@ -344,10 +344,14 @@ else if (func == FUNC_ADJUST_GVAR) { switch (CFN_GVAR_MODE(cfn)) { case FUNC_ADJUST_GVAR_CONSTANT: + { + uint8_t gvar_index = CFN_GVAR_INDEX(cfn); val_displayed = (int16_t)CFN_PARAM(cfn); - val_min = CFN_GVAR_CST_MIN; val_max = CFN_GVAR_CST_MAX; - lcdDrawNumber(MODEL_SPECIAL_FUNC_3RD_COLUMN, y, val_displayed, attr|LEFT); + val_min = max(CFN_GVAR_CST_MIN, MODEL_GVAR_MIN(gvar_index)); + val_max = min(CFN_GVAR_CST_MAX, MODEL_GVAR_MAX(gvar_index)); + drawGVarValue(MODEL_SPECIAL_FUNC_3RD_COLUMN, y, gvar_index, val_displayed, attr|LEFT); break; + } case FUNC_ADJUST_GVAR_SOURCE: val_max = MIXSRC_LAST_CH; drawSource(MODEL_SPECIAL_FUNC_3RD_COLUMN, y, val_displayed, attr); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/model_telemetry.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/model_telemetry.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/model_telemetry.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/model_telemetry.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -25,6 +25,7 @@ ITEM_TELEMETRY_RSSI_LABEL, ITEM_TELEMETRY_RSSI_ALARM1, ITEM_TELEMETRY_RSSI_ALARM2, + ITEM_TELEMETRY_DISABLE_ALARMS, ITEM_TELEMETRY_SENSORS_LABEL, ITEM_TELEMETRY_SENSOR1, ITEM_TELEMETRY_SENSOR2, @@ -73,7 +74,7 @@ #define TELEM_COL1 (1*FW) #define TELEM_COL2 (16*FW) -#define TELEM_COL3 (28*FW+2) +#define TELEM_COL3 (30*FW+2) #define IF_FAS_OFFSET(x) x, #define IS_RANGE_DEFINED(k) (g_model.frsky.channels[k].ratio > 0) @@ -85,9 +86,9 @@ #else #define VARIO_ROWS #endif -#define RSSI_ROWS LABEL(RSSI), 0, 0, +#define RSSI_ROWS LABEL(RSSI), 0, 0, 0, #define VARIO_RANGE_ROWS 3 -#define TELEMETRY_TYPE_ROWS (g_model.moduleData[INTERNAL_MODULE].rfProtocol == RF_PROTO_OFF && g_model.moduleData[EXTERNAL_MODULE].type == MODULE_TYPE_PPM) ? (uint8_t)0 : HIDDEN_ROW, +#define TELEMETRY_TYPE_ROWS (!IS_INTERNAL_MODULE_ENABLED() && g_model.moduleData[EXTERNAL_MODULE].type == MODULE_TYPE_PPM) ? (uint8_t)0 : HIDDEN_ROW, enum SensorFields { SENSOR_FIELD_NAME, @@ -515,7 +516,7 @@ case ITEM_TELEMETRY_RSSI_LABEL: #if defined(MULTIMODULE) - if (g_model.moduleData[INTERNAL_MODULE].rfProtocol == RF_PROTO_OFF && + if (g_model.moduleData[INTERNAL_MODULE].type != MODULE_TYPE_XJT && g_model.moduleData[EXTERNAL_MODULE].type == MODULE_TYPE_MULTIMODULE && g_model.moduleData[EXTERNAL_MODULE].getMultiProtocol(false) == MM_RF_PROTO_FS_AFHDS2A) lcdDrawTextAlignedLeft(y, PSTR("RSNR")); @@ -526,14 +527,20 @@ case ITEM_TELEMETRY_RSSI_ALARM1: case ITEM_TELEMETRY_RSSI_ALARM2: { - uint8_t alarm = k-ITEM_TELEMETRY_RSSI_ALARM1; - lcdDrawTextAlignedLeft(y, (alarm==0 ? STR_LOWALARM : STR_CRITICALALARM)); - lcdDrawNumber(TELEM_COL2, y, getRssiAlarmValue(alarm), LEFT|attr, 3); + bool warning = (k==ITEM_TELEMETRY_RSSI_ALARM1); + lcdDrawTextAlignedLeft(y, (warning ? STR_LOWALARM : STR_CRITICALALARM)); + lcdDrawNumber(TELEM_COL2, y, warning? g_model.rssiAlarms.getWarningRssi() : g_model.rssiAlarms.getCriticalRssi(), LEFT|attr, 3); if (attr && s_editMode>0) { - CHECK_INCDEC_MODELVAR(event, g_model.frsky.rssiAlarms[alarm].value, -30, 30); + if (warning) + CHECK_INCDEC_MODELVAR(event, g_model.rssiAlarms.warning, -30, 30); + else + CHECK_INCDEC_MODELVAR(event, g_model.rssiAlarms.critical, -30, 30); } break; } + case ITEM_TELEMETRY_DISABLE_ALARMS: + g_model.rssiAlarms.disabled = editCheckBox(g_model.rssiAlarms.disabled, TELEM_COL3, y, STR_DISABLE_ALARM, attr, event); + break; #if defined(VARIO) case ITEM_TELEMETRY_VARIO_LABEL: diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/popups.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/popups.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/popups.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/popups.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -83,6 +83,8 @@ lcdRefresh(); lcdSetContrast(); clearKeyEvents(); + backlightOn(); + checkBacklight(); } void runPopupWarning(event_t event) diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/radio_diaganas.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/radio_diaganas.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/radio_diaganas.cpp 2017-04-29 16:57:04.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/radio_diaganas.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -42,8 +42,11 @@ } // SWR - if((IS_MODULE_XJT(INTERNAL_MODULE) && IS_INTERNAL_MODULE_ON()) || (IS_MODULE_XJT(EXTERNAL_MODULE) && !IS_INTERNAL_MODULE_ON())) { + if((IS_MODULE_XJT(INTERNAL_MODULE) && IS_INTERNAL_MODULE_ON()) || (IS_MODULE_PXX(EXTERNAL_MODULE) && !IS_INTERNAL_MODULE_ON())) { lcdDrawTextAlignedLeft(MENU_HEADER_HEIGHT+6*FH, "RAS"); lcdDrawNumber(10*FW-1, MENU_HEADER_HEIGHT+6*FH, telemetryData.swr.value, RIGHT); + lcdDrawText(LCD_W/2, MENU_HEADER_HEIGHT+6*FH, "XJTVER"); + lcdDrawNumber(LCD_W/2 + 10*FW-1, MENU_HEADER_HEIGHT+6*FH, telemetryData.xjtVersion, RIGHT); + } } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/radio_diagkeys.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/radio_diagkeys.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/radio_diagkeys.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/radio_diagkeys.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -37,7 +37,7 @@ if (i<8) { y = MENU_HEADER_HEIGHT + FH*3 + FH*(i/2); - if (i&1) lcd_img(14*FW, y, sticks, i/2, 0); + if (i&1) lcdDraw1bitBitmap(14*FW, y, sticks, i/2, 0); displayKeyState(i&1? 20*FW : 18*FW, y, TRM_BASE+i); } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/radio_hardware.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/radio_hardware.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/radio_hardware.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/radio_hardware.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -54,7 +54,8 @@ CASE_PCBX9E(ITEM_RADIO_HARDWARE_SP) CASE_PCBX9E(ITEM_RADIO_HARDWARE_SQ) CASE_PCBX9E(ITEM_RADIO_HARDWARE_SR) - CASE_PCBX9E(ITEM_RADIO_HARDWARE_BLUETOOTH) + CASE_BLUETOOTH(ITEM_RADIO_HARDWARE_BLUETOOTH_MODE) + CASE_BLUETOOTH(ITEM_RADIO_HARDWARE_BLUETOOTH_NAME) ITEM_RADIO_HARDWARE_UART3_MODE, ITEM_RADIO_HARDWARE_JITTER_FILTER, ITEM_RADIO_HARDWARE_MAX @@ -72,9 +73,13 @@ #if defined(PCBX9E) #define SWITCHES_ROWS NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1 - #define BLUETOOTH_ROWS 1, #else #define SWITCHES_ROWS NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1 +#endif + +#if defined(BLUETOOTH) && defined(USEHORUSBT) + #define BLUETOOTH_ROWS 0, uint8_t(g_eeGeneral.bluetoothMode == BLUETOOTH_OFF ? -1 : 0), +#else #define BLUETOOTH_ROWS #endif @@ -153,6 +158,7 @@ g_eeGeneral.potsConfig |= (potType << shift); break; } + case ITEM_RADIO_HARDWARE_LABEL_SWITCHES: lcdDrawTextAlignedLeft(y, STR_SWITCHES); break; @@ -191,22 +197,29 @@ } break; } -#if defined(PCBX9E) - case ITEM_RADIO_HARDWARE_BLUETOOTH: - lcdDrawTextAlignedLeft(y, "Bluetooth"); - drawCheckBox(HW_SETTINGS_COLUMN, y, g_eeGeneral.bluetoothEnable, menuHorizontalPosition == 0 ? attr : 0); - if (attr && menuHorizontalPosition == 0) { - g_eeGeneral.bluetoothEnable = checkIncDecGen(event, g_eeGeneral.bluetoothEnable, 0, 1); - } - editName(HW_SETTINGS_COLUMN+5*FW, y, g_eeGeneral.bluetoothName, LEN_BLUETOOTH_NAME, event, menuHorizontalPosition == 1 ? attr : 0); - break; + +#if defined(BLUETOOTH) && defined(USEHORUSBT) + case ITEM_RADIO_HARDWARE_BLUETOOTH_MODE: + lcdDrawText(INDENT_WIDTH, y, STR_BLUETOOTH); + lcdDrawTextAtIndex(HW_SETTINGS_COLUMN, y, STR_BLUETOOTH_MODES, g_eeGeneral.bluetoothMode, attr); + if (attr) { + g_eeGeneral.bluetoothMode = checkIncDecGen(event, g_eeGeneral.bluetoothMode, BLUETOOTH_OFF, BLUETOOTH_TRAINER); + } + break; + + case ITEM_RADIO_HARDWARE_BLUETOOTH_NAME: + lcdDrawText(INDENT_WIDTH, y, STR_NAME); + editName(HW_SETTINGS_COLUMN, y, g_eeGeneral.bluetoothName, LEN_BLUETOOTH_NAME, event, attr); + break; #endif + case ITEM_RADIO_HARDWARE_UART3_MODE: g_eeGeneral.serial2Mode = editChoice(HW_SETTINGS_COLUMN, y, STR_UART3MODE, STR_UART3MODES, g_eeGeneral.serial2Mode, 0, UART_MODE_MAX, attr, event); if (attr && checkIncDec_Ret) { serial2Init(g_eeGeneral.serial2Mode, modelTelemetryProtocol()); } break; + case ITEM_RADIO_HARDWARE_JITTER_FILTER: { uint8_t b = 1-g_eeGeneral.jitterFilter; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/radio_setup.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/radio_setup.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/radio_setup.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/radio_setup.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -70,6 +70,7 @@ ITEM_SETUP_INACTIVITY_ALARM, ITEM_SETUP_MEMORY_WARNING, ITEM_SETUP_ALARM_WARNING, + ITEM_SETUP_RSSI_POWEROFF_ALARM, ITEM_SETUP_BACKLIGHT_LABEL, ITEM_SETUP_BACKLIGHT_MODE, ITEM_SETUP_BACKLIGHT_DELAY, @@ -87,6 +88,7 @@ IF_FAI_CHOICE(ITEM_SETUP_FAI) CASE_MAVLINK(ITEM_MAVLINK_BAUD) ITEM_SETUP_SWITCHES_DELAY, + ITEM_SETUP_USB_MODE, ITEM_SETUP_RX_CHANNEL_ORD, ITEM_SETUP_STICK_MODE_LABELS, ITEM_SETUP_STICK_MODE, @@ -115,7 +117,7 @@ } #endif - MENU(STR_MENURADIOSETUP, menuTabGeneral, MENU_RADIO_SETUP, ITEM_SETUP_MAX, { 2, 2, 0, 1, LABEL(SOUND), 0, 0, 0, 0, 0, 0, 0, CASE_VARIO(LABEL(VARIO)) CASE_VARIO(0) CASE_VARIO(0) CASE_VARIO(0) CASE_VARIO(0) CASE_HAPTIC(LABEL(HAPTIC)) CASE_HAPTIC(0) CASE_HAPTIC(0) CASE_HAPTIC(0) 0, LABEL(ALARMS), 0, 0, 0, 0, IF_ROTARY_ENCODERS(0) LABEL(BACKLIGHT), 0, 0, 0, CASE_PCBX9E_PCBX9DP(0) CASE_PWM_BACKLIGHT(0) CASE_PWM_BACKLIGHT(0) 0, CASE_SPLASH_PARAM(0) CASE_GPS(LABEL(GPS)) CASE_GPS(0) CASE_GPS(0) CASE_GPS(0) CASE_PXX(0) 0, 0, IF_FAI_CHOICE(0) CASE_MAVLINK(0) 0, 0, LABEL(TX_MODE), 0, 1/*to force edit mode*/ }); + MENU(STR_MENURADIOSETUP, menuTabGeneral, MENU_RADIO_SETUP, ITEM_SETUP_MAX, { 2, 2, 0, 1, LABEL(SOUND), 0, 0, 0, 0, 0, 0, 0, CASE_VARIO(LABEL(VARIO)) CASE_VARIO(0) CASE_VARIO(0) CASE_VARIO(0) CASE_VARIO(0) CASE_HAPTIC(LABEL(HAPTIC)) CASE_HAPTIC(0) CASE_HAPTIC(0) CASE_HAPTIC(0) 0, LABEL(ALARMS), 0, 0, 0, 0, 0,IF_ROTARY_ENCODERS(0) LABEL(BACKLIGHT), 0, 0, 0, CASE_PCBX9E_PCBX9DP(0) 0, CASE_SPLASH_PARAM(0) CASE_GPS(LABEL(GPS)) CASE_GPS(0) CASE_GPS(0) CASE_GPS(0) CASE_PXX(0) 0, 0, IF_FAI_CHOICE(0) CASE_MAVLINK(0) 0, 0, 0, LABEL(TX_MODE), 0, 1/*to force edit mode*/ }); if (event == EVT_ENTRY) { reusableBuffer.generalSettings.stickMode = g_eeGeneral.stickMode; @@ -331,18 +333,25 @@ case ITEM_SETUP_MEMORY_WARNING: { - uint8_t b = 1-g_eeGeneral.disableMemoryWarning; + uint8_t b = 1 - g_eeGeneral.disableMemoryWarning; g_eeGeneral.disableMemoryWarning = 1 - editCheckBox(b, RADIO_SETUP_2ND_COLUMN, y, STR_MEMORYWARNING, attr, event); break; } case ITEM_SETUP_ALARM_WARNING: { - uint8_t b = 1-g_eeGeneral.disableAlarmWarning; + uint8_t b = 1 - g_eeGeneral.disableAlarmWarning; g_eeGeneral.disableAlarmWarning = 1 - editCheckBox(b, RADIO_SETUP_2ND_COLUMN, y, STR_ALARMWARNING, attr, event); break; } + case ITEM_SETUP_RSSI_POWEROFF_ALARM: + { + uint8_t b = 1 - g_eeGeneral.disableRssiPoweroffAlarm; + g_eeGeneral.disableRssiPoweroffAlarm = 1 - editCheckBox(b, RADIO_SETUP_2ND_COLUMN, y, STR_RSSISHUTDOWNALARM, attr, event); + break; + } + case ITEM_SETUP_INACTIVITY_ALARM: lcdDrawTextAlignedLeft(y, STR_INACTIVITYALARM); lcdDrawNumber(RADIO_SETUP_2ND_COLUMN, y, g_eeGeneral.inactivityTimer, attr|LEFT); @@ -470,6 +479,10 @@ if (attr) CHECK_INCDEC_GENVAR(event, g_eeGeneral.switchesDelay, -15, 100-15); break; + case ITEM_SETUP_USB_MODE: + g_eeGeneral.USBMode = editChoice(RADIO_SETUP_2ND_COLUMN, y, STR_USBMODE, STR_USBMODES, g_eeGeneral.USBMode, USB_UNSELECTED_MODE, USB_MAX_MODE, attr, event); + break; + case ITEM_SETUP_RX_CHANNEL_ORD: lcdDrawTextAlignedLeft(y, STR_RXCHANNELORD); // RAET->AETR for (uint8_t i=1; i<=4; i++) { @@ -481,7 +494,7 @@ case ITEM_SETUP_STICK_MODE_LABELS: lcdDrawTextAlignedLeft(y, NO_INDENT(STR_MODE)); for (uint8_t i=0; i<4; i++) { - lcd_img((6+4*i)*FW, y, sticks, i, 0); + lcdDraw1bitBitmap((6+4*i)*FW, y, sticks, i, 0); } break; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/view_channels.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/view_channels.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/view_channels.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/view_channels.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -40,6 +40,10 @@ break; case EVT_KEY_FIRST(KEY_RIGHT): case EVT_KEY_FIRST(KEY_LEFT): +#if defined(ROTARY_ENCODER_NAVIGATION) + case EVT_ROTARY_LEFT: + case EVT_ROTARY_RIGHT: +#endif secondPage = !secondPage; break; case EVT_KEY_FIRST(KEY_ENTER): diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/view_main.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/view_main.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/view_main.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/view_main.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -299,7 +299,7 @@ /* The inside of the RSSI gauge */ if (TELEMETRY_RSSI() > 0) { - displayTopBarGauge(batt_icon_x+5*FW, TELEMETRY_RSSI() / 10, TELEMETRY_RSSI() < getRssiAlarmValue(0)); + displayTopBarGauge(batt_icon_x+5*FW, TELEMETRY_RSSI() / 10, TELEMETRY_RSSI() < g_model.rssiAlarms.getWarningRssi()); } } @@ -433,6 +433,8 @@ void menuMainView(event_t event) { + static bool secondPage = false; + STICK_SCROLL_DISABLE(); switch(event) { @@ -491,6 +493,15 @@ } #endif break; + + case EVT_KEY_FIRST(KEY_RIGHT): + case EVT_KEY_FIRST(KEY_LEFT): +#if defined(ROTARY_ENCODER_NAVIGATION) + case EVT_ROTARY_LEFT: + case EVT_ROTARY_RIGHT: +#endif + secondPage = !secondPage; + break; } // Flight Mode Name @@ -548,11 +559,17 @@ } else { // Logical Switches - lcdDrawText(TRIM_RH_X - TRIM_LEN/2 + 5, 6*FH-1, "LS 1-32"); - for (int sw=0; sw<32; ++sw) { - div_t qr = div(sw, 10); - uint8_t y = 13 + 11 * qr.quot; - uint8_t x = TRIM_RH_X - TRIM_LEN + qr.rem*5 + (qr.rem >= 5 ? 3 : 0); + int sw = (secondPage && MAX_LOGICAL_SWITCHES > 32 ? 32 : 0); + const int end = sw + 32; + uint8_t y = 6*FH-1; + lcdDrawText(TRIM_RH_X - TRIM_LEN/2 + 1, y, "LS"); + lcdDrawNumber(lcdLastRightPos + 1, y, sw + 1, LEFT|LEADING0, 2); + lcdDrawText(lcdLastRightPos, y, "-"); + lcdDrawNumber(lcdLastRightPos, y, end, LEFT); + for ( ; sw < end; ++sw) { + const div_t qr = div(sw + 32 - end, 10); + const uint8_t x = TRIM_RH_X - TRIM_LEN + qr.rem*5 + (qr.rem >= 5 ? 3 : 0); + y = 13 + 11 * qr.quot; LogicalSwitchData * cs = lswAddress(sw); if (cs->func == LS_FUNC_NONE) { lcdDrawSolidHorizontalLine(x, y+6, 4); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/view_statistics.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/view_statistics.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/view_statistics.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/view_statistics.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -2,7 +2,7 @@ * Copyright (C) OpenTX * * Based on code named - * th9x - http://code.google.com/p/th9x + * th9x - http://code.google.com/p/th9x * er9x - http://code.google.com/p/er9x * gruvin9x - http://code.google.com/p/gruvin9x * @@ -32,10 +32,22 @@ switch(event) { case EVT_KEY_FIRST(KEY_UP): + case EVT_KEY_BREAK(KEY_PAGE): chainMenu(menuStatisticsDebug); break; - case EVT_KEY_LONG(KEY_MENU): + case EVT_KEY_FIRST(KEY_DOWN): + case EVT_KEY_LONG(KEY_PAGE): + killEvents(event); +#if defined(DEBUG_TRACE_BUFFER) + chainMenu(menuTraceBuffer); +#else + chainMenu(menuStatisticsDebug2); +#endif + break; + + case EVT_KEY_LONG(KEY_MENU): // historical + case EVT_KEY_LONG(KEY_ENTER): g_eeGeneral.globalTimer = 0; storageDirty(EE_GENERAL); sessionTimer = 0; @@ -85,18 +97,11 @@ } #define MENU_DEBUG_COL1_OFS (11*FW-2) -#define MENU_DEBUG_Y_MIXMAX (2*FH-3) -#define MENU_DEBUG_Y_LUA (3*FH-2) -#define MENU_DEBUG_Y_FREE_RAM (4*FH-1) -#define MENU_DEBUG_Y_USB (5*FH) -#define MENU_DEBUG_Y_RTOS (6*FH) - -#if defined(USB_SERIAL) - extern uint16_t usbWraps; - extern uint16_t charsWritten; - extern "C" volatile uint32_t APP_Rx_ptr_in; - extern "C" volatile uint32_t APP_Rx_ptr_out; -#endif +#define MENU_DEBUG_ROW1 (2*FH-3) +#define MENU_DEBUG_ROW2 (3*FH-2) +#define MENU_DEBUG_ROW3 (4*FH-1) +#define MENU_DEBUG_ROW4 (5*FH) +#define MENU_DEBUG_ROW5 (6*FH) void menuStatisticsDebug(event_t event) { @@ -127,15 +132,17 @@ maxMixerDuration = 0; break; -#if defined(DEBUG_TRACE_BUFFER) - case EVT_KEY_FIRST(KEY_UP): - pushMenu(menuTraceBuffer); - return; -#endif - case EVT_KEY_FIRST(KEY_DOWN): + case EVT_KEY_LONG(KEY_PAGE): + killEvents(event); chainMenu(menuStatisticsView); break; + + case EVT_KEY_FIRST(KEY_UP): + case EVT_KEY_BREAK(KEY_PAGE): + chainMenu(menuStatisticsDebug2); + break; + case EVT_KEY_FIRST(KEY_EXIT): chainMenu(menuMainView); break; @@ -150,47 +157,89 @@ #endif } - lcdDrawTextAlignedLeft(MENU_DEBUG_Y_FREE_RAM, "Free Mem"); - lcdDrawNumber(MENU_DEBUG_COL1_OFS, MENU_DEBUG_Y_FREE_RAM, availableMemory(), LEFT); - lcdDrawText(lcdLastRightPos, MENU_DEBUG_Y_FREE_RAM, "b"); + lcdDrawTextAlignedLeft(MENU_DEBUG_ROW3, "Free Mem"); + lcdDrawNumber(MENU_DEBUG_COL1_OFS, MENU_DEBUG_ROW3, availableMemory(), LEFT); + lcdDrawText(lcdLastRightPos, MENU_DEBUG_ROW3, "b"); #if defined(LUA) - lcdDrawTextAlignedLeft(MENU_DEBUG_Y_LUA, "Lua scripts"); - lcdDrawText(MENU_DEBUG_COL1_OFS, MENU_DEBUG_Y_LUA+1, "[Duration]", SMLSIZE); - lcdDrawNumber(lcdLastRightPos, MENU_DEBUG_Y_LUA, 10*maxLuaDuration, LEFT); - lcdDrawText(lcdLastRightPos+2, MENU_DEBUG_Y_LUA+1, "[Interval]", SMLSIZE); - lcdDrawNumber(lcdLastRightPos, MENU_DEBUG_Y_LUA, 10*maxLuaInterval, LEFT); -#endif - - lcdDrawTextAlignedLeft(MENU_DEBUG_Y_MIXMAX, STR_TMIXMAXMS); - lcdDrawNumber(MENU_DEBUG_COL1_OFS, MENU_DEBUG_Y_MIXMAX, DURATION_MS_PREC2(maxMixerDuration), PREC2|LEFT); - lcdDrawText(lcdLastRightPos, MENU_DEBUG_Y_MIXMAX, "ms"); - -#if !defined(SIMU) && defined(USB_SERIAL) - lcdDrawTextAlignedLeft(MENU_DEBUG_Y_USB, "Usb"); - lcdDrawNumber(MENU_DEBUG_COL1_OFS, MENU_DEBUG_Y_USB, charsWritten, LEFT); - lcdDrawText(lcdLastRightPos, MENU_DEBUG_Y_USB, " "); - lcdDrawNumber(lcdLastRightPos, MENU_DEBUG_Y_USB, APP_Rx_ptr_in, LEFT); - lcdDrawText(lcdLastRightPos, MENU_DEBUG_Y_USB, " "); - lcdDrawNumber(lcdLastRightPos, MENU_DEBUG_Y_USB, APP_Rx_ptr_out, LEFT); - lcdDrawText(lcdLastRightPos, MENU_DEBUG_Y_USB, " "); - lcdDrawNumber(lcdLastRightPos, MENU_DEBUG_Y_USB, usbWraps, LEFT); -#endif - - lcdDrawTextAlignedLeft(MENU_DEBUG_Y_RTOS, STR_FREESTACKMINB); - lcdDrawText(MENU_DEBUG_COL1_OFS, MENU_DEBUG_Y_RTOS+1, "[M]", SMLSIZE); - lcdDrawNumber(lcdLastRightPos, MENU_DEBUG_Y_RTOS, menusStack.available(), LEFT); - lcdDrawText(lcdLastRightPos+2, MENU_DEBUG_Y_RTOS+1, "[X]", SMLSIZE); - lcdDrawNumber(lcdLastRightPos, MENU_DEBUG_Y_RTOS, mixerStack.available(), LEFT); - lcdDrawText(lcdLastRightPos+2, MENU_DEBUG_Y_RTOS+1, "[A]", SMLSIZE); - lcdDrawNumber(lcdLastRightPos, MENU_DEBUG_Y_RTOS, audioStack.available(), LEFT); - lcdDrawText(lcdLastRightPos+2, MENU_DEBUG_Y_RTOS+1, "[I]", SMLSIZE); - lcdDrawNumber(lcdLastRightPos, MENU_DEBUG_Y_RTOS, stackAvailable(), LEFT); + lcdDrawTextAlignedLeft(MENU_DEBUG_ROW2, "Lua scripts"); + lcdDrawText(MENU_DEBUG_COL1_OFS, MENU_DEBUG_ROW2+1, "[Duration]", SMLSIZE); + lcdDrawNumber(lcdLastRightPos, MENU_DEBUG_ROW2, 10*maxLuaDuration, LEFT); + lcdDrawText(lcdLastRightPos+2, MENU_DEBUG_ROW2+1, "[Interval]", SMLSIZE); + lcdDrawNumber(lcdLastRightPos, MENU_DEBUG_ROW2, 10*maxLuaInterval, LEFT); +#endif + + lcdDrawTextAlignedLeft(MENU_DEBUG_ROW1, STR_TMIXMAXMS); + lcdDrawNumber(MENU_DEBUG_COL1_OFS, MENU_DEBUG_ROW1, DURATION_MS_PREC2(maxMixerDuration), PREC2|LEFT); + lcdDrawText(lcdLastRightPos, MENU_DEBUG_ROW1, "ms"); + +#if !defined(SIMU) && defined(DEBUG) + lcdDrawTextAlignedLeft(MENU_DEBUG_ROW4, "Usb"); + lcdDrawNumber(MENU_DEBUG_COL1_OFS, MENU_DEBUG_ROW4, charsWritten, LEFT); + lcdDrawText(lcdLastRightPos, MENU_DEBUG_ROW4, " "); + lcdDrawNumber(lcdLastRightPos, MENU_DEBUG_ROW4, APP_Rx_ptr_in, LEFT); + lcdDrawText(lcdLastRightPos, MENU_DEBUG_ROW4, " "); + lcdDrawNumber(lcdLastRightPos, MENU_DEBUG_ROW4, APP_Rx_ptr_out, LEFT); + lcdDrawText(lcdLastRightPos, MENU_DEBUG_ROW4, " "); + lcdDrawNumber(lcdLastRightPos, MENU_DEBUG_ROW4, usbWraps, LEFT); +#endif + + lcdDrawTextAlignedLeft(MENU_DEBUG_ROW5, STR_FREESTACKMINB); + lcdDrawText(MENU_DEBUG_COL1_OFS, MENU_DEBUG_ROW5+1, "[M]", SMLSIZE); + lcdDrawNumber(lcdLastRightPos, MENU_DEBUG_ROW5, menusStack.available(), LEFT); + lcdDrawText(lcdLastRightPos+2, MENU_DEBUG_ROW5+1, "[X]", SMLSIZE); + lcdDrawNumber(lcdLastRightPos, MENU_DEBUG_ROW5, mixerStack.available(), LEFT); + lcdDrawText(lcdLastRightPos+2, MENU_DEBUG_ROW5+1, "[A]", SMLSIZE); + lcdDrawNumber(lcdLastRightPos, MENU_DEBUG_ROW5, audioStack.available(), LEFT); + lcdDrawText(lcdLastRightPos+2, MENU_DEBUG_ROW5+1, "[I]", SMLSIZE); + lcdDrawNumber(lcdLastRightPos, MENU_DEBUG_ROW5, stackAvailable(), LEFT); lcdDrawText(3*FW, 7*FH+1, STR_MENUTORESET); lcdInvertLastLine(); } +void menuStatisticsDebug2(event_t event) +{ + TITLE(STR_MENUDEBUG); + + switch(event) + { + + + + case EVT_KEY_FIRST(KEY_UP): + case EVT_KEY_BREAK(KEY_PAGE): +#if defined(DEBUG_TRACE_BUFFER) + chainMenu(menuTraceBuffer); +#else + chainMenu(menuStatisticsView); +#endif + return; + + case EVT_KEY_FIRST(KEY_DOWN): + case EVT_KEY_LONG(KEY_PAGE): + killEvents(event); + chainMenu(menuStatisticsDebug); + break; + + + case EVT_KEY_FIRST(KEY_EXIT): + chainMenu(menuMainView); + break; + + case EVT_KEY_LONG(KEY_ENTER): + telemetryErrors = 0; + break; + } + + // UART statistics + lcdDrawTextAlignedLeft(MENU_DEBUG_ROW1, "Tlm RX Err"); + lcdDrawNumber(MENU_DEBUG_COL1_OFS, MENU_DEBUG_ROW1, telemetryErrors, RIGHT); + + + lcdDrawText(3*FW, 7*FH+1, STR_MENUTORESET); + lcdInvertLastLine(); +} #if defined(DEBUG_TRACE_BUFFER) void menuTraceBuffer(event_t event) @@ -201,6 +250,17 @@ dumpTraceBuffer(); killEvents(event); break; + + case EVT_KEY_FIRST(KEY_DOWN): + case EVT_KEY_LONG(KEY_PAGE): + killEvents(event); + chainMenu(menuStatisticsDebug2); + break; + + case EVT_KEY_FIRST(KEY_UP): + case EVT_KEY_BREAK(KEY_PAGE): + chainMenu(menuStatisticsView); + return; } SIMPLE_SUBMENU("Trace Buffer", TRACE_BUFFER_LEN); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/view_telemetry.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/view_telemetry.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/view_telemetry.cpp 2017-04-27 08:57:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/view_telemetry.cpp 2017-11-10 17:23:25.000000000 +0000 @@ -36,7 +36,7 @@ lcdDrawSizedText(0, STATUS_BAR_Y, STR_RX, 2); lcdDrawNumber(4*FW, STATUS_BAR_Y, rssi, LEADING0|RIGHT, 2); lcdDrawRect(BAR_LEFT, 57, 78, 7); - lcdDrawFilledRect(BAR_LEFT+1, 58, 19*rssi/25, 5, (rssi < getRssiAlarmValue(0)) ? DOTTED : SOLID); + lcdDrawFilledRect(BAR_LEFT+1, 58, 19*rssi/25, 5, (rssi < g_model.rssiAlarms.getWarningRssi()) ? DOTTED : SOLID); } else { lcdDrawText(7*FW, STATUS_BAR_Y, STR_NODATA, BLINK); @@ -144,7 +144,12 @@ } } - drawSourceValue(x, y, field, att); + if(isSensorUnit(1+(field-MIXSRC_FIRST_TELEM)/3, UNIT_DATETIME) && field >= MIXSRC_FIRST_TELEM) { + drawTelemScreenDate(x, y, field, att); + } + else { + drawSourceValue(x, y, field, att); + } } } } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/widgets.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/widgets.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/212x64/widgets.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/212x64/widgets.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -2,7 +2,7 @@ * Copyright (C) OpenTX * * Based on code named - * th9x - http://code.google.com/p/th9x + * th9x - http://code.google.com/p/th9x * er9x - http://code.google.com/p/er9x * gruvin9x - http://code.google.com/p/gruvin9x * @@ -20,7 +20,7 @@ #include "opentx.h" -const pm_uchar bmp_sleep[] PROGMEM = { +const pm_uchar SLEEP_BITMAP[] PROGMEM = { #include "../../bitmaps/212x64/sleep.lbm" }; @@ -29,23 +29,26 @@ void drawSleepBitmap() { lcdClear(); - lcdDrawBitmap((LCD_W-SLEEP_BITMAP_WIDTH)/2, (LCD_H-SLEEP_BITMAP_HEIGHT)/2, bmp_sleep, 0, SLEEP_BITMAP_WIDTH); + lcdDrawBitmap((LCD_W-SLEEP_BITMAP_WIDTH)/2, (LCD_H-SLEEP_BITMAP_HEIGHT)/2, SLEEP_BITMAP, 0, SLEEP_BITMAP_WIDTH); lcdRefresh(); } #if defined(PWR_BUTTON_PRESS) -const pm_uchar bmp_shutdown[] PROGMEM = { +const pm_uchar SHUTDOWN_BITMAP[] PROGMEM = { #include "../../bitmaps/212x64/shutdown.lbm" }; #define SHUTDOWN_BITMAP_WIDTH 60 #define SHUTDOWN_BITMAP_HEIGHT 60 -void drawShutdownAnimation(uint32_t index) +void drawShutdownAnimation(uint32_t index, const char * message) { index /= (PWR_PRESS_SHUTDOWN_DELAY / 4); lcdRefreshWait(); lcdClear(); - lcdDrawBitmap((LCD_W-SHUTDOWN_BITMAP_WIDTH)/2, (LCD_H-SHUTDOWN_BITMAP_HEIGHT)/2, bmp_shutdown, index * SHUTDOWN_BITMAP_WIDTH, SHUTDOWN_BITMAP_WIDTH); + lcdDrawBitmap((LCD_W-SHUTDOWN_BITMAP_WIDTH)/2, (LCD_H-SHUTDOWN_BITMAP_HEIGHT)/2, SHUTDOWN_BITMAP, (3 - index) * SHUTDOWN_BITMAP_WIDTH, SHUTDOWN_BITMAP_WIDTH); + if (message) { + lcdDrawText((LCD_W - getTextWidth(message)) / 2, LCD_H-2*FH, message); + } lcdRefresh(); } #endif diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/bitmapbuffer.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/bitmapbuffer.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/bitmapbuffer.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/bitmapbuffer.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -436,7 +436,7 @@ for (int y=h2-1; y>=0; y--) { for (int x=w2-1; x>=0; x--) { - int slope = (x==0 ? (y<0 ? -99000 : 99000) : y*100/x); + int slope = (x==0 ? 99000 : y*100/x); if (slope >= slopes[0] && slope < slopes[1]) { *getPixelPtr(x0+w2+x, y0+h2-y) = q[(h2-y)*width + w2+x]; } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/bitmapbuffer.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/bitmapbuffer.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/bitmapbuffer.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/bitmapbuffer.h 2017-11-20 18:43:59.000000000 +0000 @@ -24,7 +24,7 @@ #include #include "colors.h" -#if defined(PCBX10) +#if defined(PCBX10) && !defined(SIMU) #define MOVE_PIXEL_RIGHT(p, count) p -= count #else #define MOVE_PIXEL_RIGHT(p, count) p += count @@ -86,7 +86,7 @@ inline const display_t * getPixelPtr(coord_t x, coord_t y) const { -#if defined(PCBX10) +#if defined(PCBX10) && !defined(SIMU) x = width - x - 1; y = height - y - 1; #endif @@ -165,7 +165,7 @@ inline const display_t * getPixelPtr(coord_t x, coord_t y) const { -#if defined(PCBX10) +#if defined(PCBX10) && !defined(SIMU) x = width - x - 1; y = height - y - 1; #endif @@ -174,7 +174,7 @@ inline display_t * getPixelPtr(coord_t x, coord_t y) { -#if defined(PCBX10) +#if defined(PCBX10) && !defined(SIMU) x = width - x - 1; y = height - y - 1; #endif @@ -216,7 +216,7 @@ if (!data || h==0 || w==0) return; if (h<0) { y+=h; h=-h; } if (w<0) { x+=w; w=-w; } - DMAFillRect(data, width, height, x, y, w, h, lcdColorTable[COLOR_IDX(flags)]); + DMAFillRect(data, width, height, (x>0)?x:0, (y>0)?y:0, w, h, lcdColorTable[COLOR_IDX(flags)]); } void drawFilledRect(coord_t x, coord_t y, coord_t w, coord_t h, uint8_t pat, LcdFlags att); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/lcd.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/lcd.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/lcd.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/lcd.cpp 2017-11-20 18:43:59.000000000 +0000 @@ -307,12 +307,13 @@ } } + void drawDate(coord_t x, coord_t y, TelemetryItem & telemetryItem, LcdFlags att) { // TODO if (att & DBLSIZE) { x -= 42; - att &= ~0x0F00; // TODO constant + att &= ~FONTSIZE_MASK; lcdDrawNumber(x, y, telemetryItem.datetime.day, att|LEADING0|LEFT, 2); lcdDrawChar(lcdNextPos-1, y, '-', att); lcdDrawNumber(lcdNextPos-1, y, telemetryItem.datetime.month, att|LEFT, 2); @@ -413,7 +414,7 @@ void DMAFillRect(uint16_t * dest, uint16_t destw, uint16_t desth, uint16_t x, uint16_t y, uint16_t w, uint16_t h, uint16_t color) { -#if defined(PCBX10) +#if defined(PCBX10) && !defined(SIMU) x = destw - (x + w); y = desth - (y + h); #endif @@ -427,7 +428,7 @@ void DMACopyBitmap(uint16_t * dest, uint16_t destw, uint16_t desth, uint16_t x, uint16_t y, const uint16_t * src, uint16_t srcw, uint16_t srch, uint16_t srcx, uint16_t srcy, uint16_t w, uint16_t h) { -#if defined(PCBX10) +#if defined(PCBX10) && !defined(SIMU) x = destw - (x + w); y = desth - (y + h); srcx = srcw - (srcx + w); @@ -441,7 +442,7 @@ void DMACopyAlphaBitmap(uint16_t * dest, uint16_t destw, uint16_t desth, uint16_t x, uint16_t y, const uint16_t * src, uint16_t srcw, uint16_t srch, uint16_t srcx, uint16_t srcy, uint16_t w, uint16_t h) { -#if defined(PCBX10) +#if defined(PCBX10) && !defined(SIMU) x = destw - (x + w); y = desth - (y + h); srcx = srcw - (srcx + w); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/lcd.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/lcd.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/lcd.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/lcd.h 2017-10-31 16:16:43.000000000 +0000 @@ -44,6 +44,7 @@ #define LEFT 0x00 /* align left */ #define CENTERED 0x04 /* align center */ #define RIGHT 0x08 /* align right */ +#define SHADOWED 0x80 /* black copy at +1 +1 */ /* drawNumber flags */ #define LEADING0 0x10 @@ -85,7 +86,8 @@ #define DBLSIZE (DBLSIZE_INDEX << 8) #define XXLSIZE (XXLSIZE_INDEX << 8) #define BOLD (STDSIZE_BOLD_INDEX << 8) -#define FONTSIZE(flags) ((flags) & 0x0f00) +#define FONTSIZE_MASK 0x0f00 +#define FONTSIZE(flags) ((flags) & FONTSIZE_MASK) #define FONTINDEX(flags) (FONTSIZE(flags) >> 8) #define TIMEBLINK 0x1000 diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/menus.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/menus.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/menus.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/menus.h 2017-11-10 17:23:25.000000000 +0000 @@ -149,10 +149,10 @@ const uint8_t STATS_ICONS[] = { ICON_STATS, ICON_STATS_THROTTLE_GRAPH, - ICON_STATS_TIMERS, + ICON_STATS_DEBUG, ICON_STATS_ANALOGS, #if defined(DEBUG_TRACE_BUFFER) - ICON_STATS_DEBUG + ICON_STATS_TIMERS #endif }; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/model_curves.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/model_curves.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/model_curves.cpp 2017-05-31 19:49:19.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/model_curves.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -140,8 +140,8 @@ newPoints[0] = points[0]; newPoints[4+count] = points[4+crv.points]; for (int i=1; i<4+count; i++) - newPoints[i] = calcRESXto100(applyCustomCurve(calc100toRESX(-100 + (i*200) / (4+count)), s_curveChan)); - if (moveCurve(s_curveChan, checkIncDec_Ret*(crv.type==CURVE_TYPE_CUSTOM?2:1))) { + newPoints[i] = calcRESXto100(applyCustomCurve(-RESX + (i * 2 * RESX) / (4 + count), s_curveChan)); + if (moveCurve(s_curveChan, checkIncDec_Ret*(crv.type==CURVE_TYPE_CUSTOM ? 2 :1))) { for (int i = 0; i < 5 + count; i++) { points[i] = newPoints[i]; if (crv.type == CURVE_TYPE_CUSTOM && i != 0 && i != 4 + count) diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/model_gvars.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/model_gvars.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/model_gvars.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/model_gvars.cpp 2017-11-15 20:54:40.000000000 +0000 @@ -20,17 +20,103 @@ #include "opentx.h" -void onGVARSMenu(const char * result) +void editGVarValue(coord_t x, coord_t y, event_t event, uint8_t gvar, uint8_t flightMode, LcdFlags flags) { - int8_t sub = menuVerticalPosition; + FlightModeData * fm = &g_model.flightModeData[flightMode]; + gvar_t & v = fm->gvars[gvar]; + int16_t vmin, vmax; + if (v > GVAR_MAX) { + uint8_t fm = v - GVAR_MAX - 1; + if (fm >= flightMode) fm++; + drawFlightMode(x, y, fm + 1, flags&(~LEFT)); + vmin = GVAR_MAX + 1; + vmax = GVAR_MAX + MAX_FLIGHT_MODES - 1; + } + else { + drawGVarValue(x, y, gvar, v, flags); + vmin = GVAR_MIN + g_model.gvars[gvar].min; + vmax = GVAR_MAX - g_model.gvars[gvar].max; + } - if (result == STR_ENABLE_POPUP) { - g_model.gvars[sub].popup = true; - storageDirty(EE_MODEL); + if (flags & INVERS) { + if (event == EVT_KEY_LONG(KEY_ENTER) && flightMode > 0) { + v = (v > GVAR_MAX ? 0 : GVAR_MAX+1); + storageDirty(EE_MODEL); + } + else if (s_editMode > 0) { + v = checkIncDec(event, v, vmin, vmax, EE_MODEL); + } } - else if (result == STR_DISABLE_POPUP) { - g_model.gvars[sub].popup = false; - storageDirty(EE_MODEL); +} + +enum GVarFields { + GVAR_FIELD_NAME, + GVAR_FIELD_UNIT, + GVAR_FIELD_PREC, + GVAR_FIELD_MIN, + GVAR_FIELD_MAX, + GVAR_FIELD_FM0, + GVAR_FIELD_LAST = GVAR_FIELD_FM0 + MAX_FLIGHT_MODES +}; + +bool menuModelGVarOne(event_t event) +{ + SIMPLE_SUBMENU(STR_GVARS, ICON_MODEL_GVARS, GVAR_FIELD_LAST); + + GVarData * gvar = &g_model.gvars[s_currIdx]; + drawStringWithIndex(50, 3+FH, STR_GV, s_currIdx+1, MENU_TITLE_COLOR, NULL, "="); + drawGVarValue(lcdNextPos + 2, 3+FH, s_currIdx, getGVarValue(s_currIdx, getFlightMode()), LEFT | MENU_TITLE_COLOR); + + for (int i=0; i 0 ? BLINK | INVERS : INVERS) : 0); + + switch (k) { + case GVAR_FIELD_NAME: + lcdDrawText(MENUS_MARGIN_LEFT, y, STR_NAME); + editName(MIXES_2ND_COLUMN, y, gvar->name, LEN_GVAR_NAME, event, attr); + break; + + case GVAR_FIELD_UNIT: + lcdDrawText(MENUS_MARGIN_LEFT, y, STR_UNIT); + gvar->unit = editChoice(MIXES_2ND_COLUMN, y, "\001-%", gvar->unit, 0, 1, attr, event); + break; + + case GVAR_FIELD_PREC: + lcdDrawText(MENUS_MARGIN_LEFT, y, STR_PRECISION); + gvar->prec = editChoice(MIXES_2ND_COLUMN, y, STR_VPREC, gvar->prec, 0, 1, attr, event); + break; + + case GVAR_FIELD_MIN: + lcdDrawText(MENUS_MARGIN_LEFT, y, STR_MIN); + drawGVarValue(MIXES_2ND_COLUMN, y, s_currIdx, GVAR_MIN+gvar->min, LEFT|attr); + if (attr) gvar->min = checkIncDec(event, GVAR_MIN+gvar->min, GVAR_MIN, GVAR_MAX-gvar->max, EE_MODEL) - GVAR_MIN; + break; + + case GVAR_FIELD_MAX: + lcdDrawText(MENUS_MARGIN_LEFT, y, STR_MAX); + drawGVarValue(MIXES_2ND_COLUMN, y, s_currIdx, GVAR_MAX-gvar->max, LEFT|attr); + if (attr) gvar->max = GVAR_MAX - checkIncDec(event, GVAR_MAX-gvar->max, GVAR_MIN+gvar->min, GVAR_MAX, EE_MODEL); + break; + + default: + drawStringWithIndex(MENUS_MARGIN_LEFT, y, STR_FP, k-GVAR_FIELD_FM0); + editGVarValue(MIXES_2ND_COLUMN, y, event, s_currIdx, k-GVAR_FIELD_FM0, LEFT|attr); + break; + } + } + + return true; +} + +void onGVARSMenu(const char * result) +{ + int sub = menuVerticalPosition; + + if (result == STR_EDIT) { + s_currIdx = sub; + pushMenu(menuModelGVarOne); } else if (result == STR_CLEAR) { for (int i=0; i0) ? BLINK|INVERS : INVERS) : 0); - coord_t x = GVARS_FM_COLUMN(j-1); - switch (j) { - case 0: - editName(MENUS_MARGIN_LEFT+50, y, g_model.gvars[i].name, LEN_GVAR_NAME, event, attr); - break; - - default: - { - FlightModeData * fm = &g_model.flightModeData[j-1]; - int16_t & v = fm->gvars[i]; - int16_t vmin, vmax; - if (v > GVAR_MAX) { - uint8_t p = v - GVAR_MAX - 1; - if (p >= j-1) p++; - drawFlightMode(x, y, p+1, attr | RIGHT | ((j-1 == curfm) ? BOLD : 0)); - vmin = GVAR_MAX+1; vmax = GVAR_MAX+MAX_FLIGHT_MODES-1; - } - else { - if (abs(v) >= 1000) - lcdDrawNumber(x, y+1, v, TINSIZE|attr|RIGHT); - else - lcdDrawNumber(x, y, v, attr | RIGHT | ((j-1 == curfm) ? BOLD : 0)); - vmin = -GVAR_MAX; vmax = GVAR_MAX; - } - if (attr) { - if (event == EVT_KEY_LONG(KEY_ENTER)) { - v = (v > GVAR_MAX ? 0 : GVAR_MAX+1); - storageDirty(EE_MODEL); - } - else if (s_editMode>0) { - v = checkIncDec(event, v, vmin, vmax, EE_MODEL); - } - } - break; - } + drawStringWithIndex(MENUS_MARGIN_LEFT-3, y, STR_GV, i+1, ((sub==i && menuHorizontalPosition<0) ? INVERS : 0)); + lcdDrawSizedText(MENUS_MARGIN_LEFT+35, y, g_model.gvars[i].name, LEN_GVAR_NAME, ZCHAR); + + for (int j=0; jgvars[i]; + + LcdFlags attr = RIGHT | ((sub == i && menuHorizontalPosition == j) ? (s_editMode > 0 ? BLINK | INVERS : INVERS) : 0); + if (j == curfm) + attr |= BOLD; + coord_t x = GVARS_FM_COLUMN(j); + coord_t yval = y; + if (v <= GVAR_MAX && (g_model.gvars[i].prec > 0 || abs(v) >= 1000 || ( abs(v) >= 100 && g_model.gvars[i].unit > 0))) { + attr |= SMLSIZE; + yval += 3; + } + if (v <= GVAR_MAX && g_model.gvars[i].unit > 0) { + x -= 9; + lcdDrawText(GVARS_FM_COLUMN(j) - 9, y+5, "%", TINSIZE); } + editGVarValue(x, yval, event, i, j, attr | NO_UNIT); } } if (menuHorizontalPosition < 0 && event==EVT_KEY_LONG(KEY_ENTER)) { killEvents(event); - if (g_model.gvars[sub].popup) - POPUP_MENU_ADD_ITEM(STR_DISABLE_POPUP); - else - POPUP_MENU_ADD_ITEM(STR_ENABLE_POPUP); + POPUP_MENU_ADD_ITEM(STR_EDIT); POPUP_MENU_ADD_ITEM(STR_CLEAR); POPUP_MENU_START(onGVARSMenu); } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/model_inputs.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/model_inputs.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/model_inputs.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/model_inputs.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -493,7 +493,7 @@ } char str[6]; - sprintf(str, "%d/%d", getExposCount(), MAX_EXPOS); + strAppendUnsigned(strAppend(strAppendUnsigned(str, getExposCount()), "/"), MAX_EXPOS, 2); lcdDrawText(MENU_TITLE_NEXT_POS, MENU_TITLE_TOP+2, str, HEADER_COLOR); sub = menuVerticalPosition; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/model_mixes.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/model_mixes.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/model_mixes.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/model_mixes.cpp 2017-11-15 20:54:40.000000000 +0000 @@ -153,7 +153,7 @@ MIX_FIELD_OFFSET, MIX_FIELD_TRIM, CASE_CURVES(MIX_FIELD_CURVE) - CASE_FLIGHT_MODES(MIX_FIELD_FLIGHT_PHASE) + CASE_FLIGHT_MODES(MIX_FIELD_FLIGHT_MODE) MIX_FIELD_SWITCH, // MIX_FIELD_WARNING, MIX_FIELD_MLTPX, @@ -235,7 +235,7 @@ break; #endif #if defined(FLIGHT_MODES) - case MIX_FIELD_FLIGHT_PHASE: + case MIX_FIELD_FLIGHT_MODE: lcdDrawText(MENUS_MARGIN_LEFT, y, STR_FLMODE); md2->flightModes = editFlightModes(MIXES_2ND_COLUMN, y, event, md2->flightModes, attr); break; @@ -515,7 +515,7 @@ } char str[6]; - sprintf(str, "%d/%d", getMixesCount(), MAX_MIXERS); + strAppendUnsigned(strAppend(strAppendUnsigned(str, getMixesCount()), "/"), MAX_MIXERS, 2); lcdDrawText(MENU_TITLE_NEXT_POS, MENU_TITLE_TOP+1, str, HEADER_COLOR); sub = menuVerticalPosition; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/model_outputs.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/model_outputs.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/model_outputs.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/model_outputs.cpp 2017-11-10 17:23:25.000000000 +0000 @@ -76,9 +76,11 @@ } else if (result == STR_COPY_STICKS_TO_OFS) { copySticksToOffset(ch); + storageDirty(EE_MODEL); } else if (result == STR_COPY_TRIMS_TO_OFS) { copyTrimsToOffset(ch); + storageDirty(EE_MODEL); } } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/model_setup.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/model_setup.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/model_setup.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/model_setup.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -71,18 +71,20 @@ ITEM_MODEL_EXTERNAL_MODULE_MODE, #if defined(MULTIMODULE) ITEM_MODEL_EXTERNAL_MODULE_STATUS, + ITEM_MODEL_EXTERNAL_MODULE_SYNCSTATUS, #endif ITEM_MODEL_EXTERNAL_MODULE_CHANNELS, ITEM_MODEL_EXTERNAL_MODULE_BIND, ITEM_MODEL_EXTERNAL_MODULE_FAILSAFE, + ITEM_MODEL_EXTERNAL_MODULE_OPTIONS, #if defined(MULTIMODULE) ITEM_MODEL_EXTERNAL_MODULE_AUTOBIND, - ITEM_MODEL_EXTERNAL_MODULE_LOWPOWER, #endif + ITEM_MODEL_EXTERNAL_MODULE_POWER, ITEM_MODEL_TRAINER_LABEL, ITEM_MODEL_TRAINER_MODE, - ITEM_MODEL_TRAINER_CHANNELS, - ITEM_MODEL_TRAINER_SETTINGS, + ITEM_MODEL_TRAINER_LINE1, + ITEM_MODEL_TRAINER_LINE2, ITEM_MODEL_SETUP_MAX }; @@ -94,32 +96,54 @@ #define MODEL_SETUP_SET_FAILSAFE_OFS 100 #define MODEL_SETUP_SLIDPOT_SPACING 45 -#if defined(BINDING_OPTIONS) +#define CURRENT_MODULE_EDITED(k) (k>=ITEM_MODEL_TRAINER_LABEL ? TRAINER_MODULE : (k>=ITEM_MODEL_EXTERNAL_MODULE_LABEL ? EXTERNAL_MODULE : INTERNAL_MODULE)) + void onBindMenu(const char * result) { - if (result == STR_BINDING_1_8_TELEM_ON) { - g_model.moduleData[INTERNAL_MODULE].pxx.receiver_telem_off = false; - g_model.moduleData[INTERNAL_MODULE].pxx.receiver_channel_9_16 = false; + uint8_t moduleIdx = CURRENT_MODULE_EDITED(menuVerticalPosition); + + if (result == STR_BINDING_25MW_CH1_8_TELEM_OFF) { + g_model.moduleData[moduleIdx].pxx.power = R9M_LBT_POWER_25; + g_model.moduleData[moduleIdx].pxx.receiver_telem_off = true; + g_model.moduleData[moduleIdx].pxx.receiver_channel_9_16 = false; + } + else if (result == STR_BINDING_25MW_CH1_8_TELEM_ON) { + g_model.moduleData[moduleIdx].pxx.power = R9M_LBT_POWER_25; + g_model.moduleData[moduleIdx].pxx.receiver_telem_off = false; + g_model.moduleData[moduleIdx].pxx.receiver_channel_9_16 = false; + } + else if (result == STR_BINDING_500MW_CH1_8_TELEM_OFF) { + g_model.moduleData[moduleIdx].pxx.power = R9M_LBT_POWER_500; + g_model.moduleData[moduleIdx].pxx.receiver_telem_off = true; + g_model.moduleData[moduleIdx].pxx.receiver_channel_9_16 = false; + } + else if (result == STR_BINDING_500MW_CH9_16_TELEM_OFF) { + g_model.moduleData[moduleIdx].pxx.power = R9M_LBT_POWER_500; + g_model.moduleData[moduleIdx].pxx.receiver_telem_off = true; + g_model.moduleData[moduleIdx].pxx.receiver_channel_9_16 = true; + } + else if (result == STR_BINDING_1_8_TELEM_ON) { + g_model.moduleData[moduleIdx].pxx.receiver_telem_off = false; + g_model.moduleData[moduleIdx].pxx.receiver_channel_9_16 = false; } else if (result == STR_BINDING_1_8_TELEM_OFF) { - g_model.moduleData[INTERNAL_MODULE].pxx.receiver_telem_off = true; - g_model.moduleData[INTERNAL_MODULE].pxx.receiver_channel_9_16 = false; + g_model.moduleData[moduleIdx].pxx.receiver_telem_off = true; + g_model.moduleData[moduleIdx].pxx.receiver_channel_9_16 = false; } else if (result == STR_BINDING_9_16_TELEM_ON) { - g_model.moduleData[INTERNAL_MODULE].pxx.receiver_telem_off = false; - g_model.moduleData[INTERNAL_MODULE].pxx.receiver_channel_9_16 = true; + g_model.moduleData[moduleIdx].pxx.receiver_telem_off = false; + g_model.moduleData[moduleIdx].pxx.receiver_channel_9_16 = true; } else if (result == STR_BINDING_9_16_TELEM_OFF) { - g_model.moduleData[INTERNAL_MODULE].pxx.receiver_telem_off = true; - g_model.moduleData[INTERNAL_MODULE].pxx.receiver_channel_9_16 = true; + g_model.moduleData[moduleIdx].pxx.receiver_telem_off = true; + g_model.moduleData[moduleIdx].pxx.receiver_channel_9_16 = true; } else { return; } - moduleFlag[INTERNAL_MODULE] = MODULE_BIND; + moduleFlag[moduleIdx] = MODULE_BIND; } -#endif void onModelSetupBitmapMenu(const char * result) { @@ -195,8 +219,6 @@ } } -#define CURRENT_MODULE_EDITED(k) (k>=ITEM_MODEL_TRAINER_LABEL ? TRAINER_MODULE : (k>=ITEM_MODEL_EXTERNAL_MODULE_LABEL ? EXTERNAL_MODULE : INTERNAL_MODULE)) - int getSwitchWarningsCount() { int count = 0; @@ -208,19 +230,16 @@ return count; } -#define IF_EXTERNAL_MODULE_XJT(x) (IS_MODULE_XJT(EXTERNAL_MODULE) ? (uint8_t)x : HIDDEN_ROW) -#define IF_INTERNAL_MODULE_ON(x) (g_model.moduleData[INTERNAL_MODULE].rfProtocol == RF_PROTO_OFF ? HIDDEN_ROW : (uint8_t)(x)) -#define IF_EXTERNAL_MODULE_ON(x) (g_model.moduleData[EXTERNAL_MODULE].type == MODULE_TYPE_NONE ? HIDDEN_ROW : (uint8_t)(x)) +#define IF_INTERNAL_MODULE_ON(x) (IS_INTERNAL_MODULE_ENABLED() ? (uint8_t)(x) : HIDDEN_ROW) +#define IF_EXTERNAL_MODULE_ON(x) (IS_EXTERNAL_MODULE_ENABLED() ? (uint8_t)(x) : HIDDEN_ROW) #define INTERNAL_MODULE_MODE_ROWS (uint8_t)0 #define INTERNAL_MODULE_CHANNELS_ROWS IF_INTERNAL_MODULE_ON(1) -#define TRAINER_CHANNELS_ROWS() IF_TRAINER_ON(1) -#define PORT_CHANNELS_ROWS(x) (x==INTERNAL_MODULE ? INTERNAL_MODULE_CHANNELS_ROWS : (x==EXTERNAL_MODULE ? EXTERNAL_MODULE_CHANNELS_ROWS : TRAINER_CHANNELS_ROWS())) +#define PORT_CHANNELS_ROWS(x) (x==INTERNAL_MODULE ? INTERNAL_MODULE_CHANNELS_ROWS : (x==EXTERNAL_MODULE ? EXTERNAL_MODULE_CHANNELS_ROWS : 1)) #define TIMER_ROWS(x) NAVIGATION_LINE_BY_LINE|1, 0, 0, 0, g_model.timers[x].countdownBeep != COUNTDOWN_SILENT ? (uint8_t)1 : (uint8_t)0 - -#define EXTERNAL_MODULE_MODE_ROWS (IS_MODULE_XJT(EXTERNAL_MODULE) || IS_MODULE_DSM2(EXTERNAL_MODULE)) ? (uint8_t)1 : IS_MODULE_MULTIMODULE(EXTERNAL_MODULE) ? MULTIMODULE_MODE_ROWS(EXTERNAL_MODULE) : (uint8_t)0 +#define EXTERNAL_MODULE_MODE_ROWS (IS_MODULE_PXX(EXTERNAL_MODULE) || IS_MODULE_DSM2(EXTERNAL_MODULE)) ? (uint8_t)1 : IS_MODULE_MULTIMODULE(EXTERNAL_MODULE) ? MULTIMODULE_MODE_ROWS(EXTERNAL_MODULE) : (uint8_t)0 #if TIMERS == 1 #define TIMERS_ROWS TIMER_ROWS(0) @@ -235,6 +254,10 @@ #define POT_WARN_ITEMS() ((g_model.potsWarnMode) ? uint8_t(NAVIGATION_LINE_BY_LINE|(NUM_POTS-1)) : (uint8_t)0) #define SLIDER_WARN_ITEMS() ((g_model.potsWarnMode) ? uint8_t(NAVIGATION_LINE_BY_LINE|(NUM_SLIDERS-1)) : (uint8_t)0) +#define TRAINER_LINE1_BLUETOOTH_M_ROWS ((bluetoothDistantAddr[0] == 0 || bluetoothState == BLUETOOTH_STATE_CONNECTED) ? (uint8_t)0 : (uint8_t)1) +#define TRAINER_LINE1_ROWS (g_model.trainerMode == TRAINER_MODE_SLAVE ? (uint8_t)1 : (g_model.trainerMode == TRAINER_MODE_MASTER_BLUETOOTH ? TRAINER_LINE1_BLUETOOTH_M_ROWS : (g_model.trainerMode == TRAINER_MODE_SLAVE_BLUETOOTH ? (uint8_t)1 : HIDDEN_ROW))) +#define TRAINER_LINE2_ROWS (g_model.trainerMode == TRAINER_MODE_SLAVE ? (uint8_t)2 : HIDDEN_ROW) + bool menuModelSetup(event_t event) { bool CURSOR_ON_CELL = (menuHorizontalPosition >= 0); @@ -258,11 +281,17 @@ IF_INTERNAL_MODULE_ON(0), LABEL(ExternalModule), EXTERNAL_MODULE_MODE_ROWS, - MULTIMODULE_STATUS_ROW + MULTIMODULE_STATUS_ROWS EXTERNAL_MODULE_CHANNELS_ROWS, - (IS_MODULE_XJT(EXTERNAL_MODULE) && !HAS_RF_PROTOCOL_MODELINDEX(g_model.moduleData[EXTERNAL_MODULE].rfProtocol)) ? (uint8_t)1 : (IS_MODULE_PPM(EXTERNAL_MODULE) || IS_MODULE_XJT(EXTERNAL_MODULE) || IS_MODULE_DSM2(EXTERNAL_MODULE) || IS_MODULE_MULTIMODULE(EXTERNAL_MODULE)) ? (uint8_t)2 : HIDDEN_ROW, - FAILSAFE_ROWS(EXTERNAL_MODULE), MULTIMODULE_MODULE_ROWS - LABEL(Trainer), 0, TRAINER_CHANNELS_ROWS(), IF_TRAINER_ON(2) }); + ((IS_MODULE_XJT(EXTERNAL_MODULE) && !HAS_RF_PROTOCOL_MODELINDEX(g_model.moduleData[EXTERNAL_MODULE].rfProtocol)) || IS_MODULE_SBUS(EXTERNAL_MODULE)) ? (uint8_t)1 : (IS_MODULE_PPM(EXTERNAL_MODULE) || IS_MODULE_PXX(EXTERNAL_MODULE) || IS_MODULE_DSM2(EXTERNAL_MODULE) || IS_MODULE_MULTIMODULE(EXTERNAL_MODULE)) ? (uint8_t)2 : HIDDEN_ROW, + FAILSAFE_ROWS(EXTERNAL_MODULE), + EXTERNAL_MODULE_OPTION_ROW, + MULTIMODULE_MODULE_ROWS + EXTERNAL_MODULE_POWER_ROW, + LABEL(Trainer), + 0, + TRAINER_LINE1_ROWS, + TRAINER_LINE2_ROWS }); if (menuEvent) { moduleFlag[0] = 0; @@ -622,7 +651,10 @@ g_model.moduleData[0].type = MODULE_TYPE_XJT; g_model.moduleData[0].channelsStart = 0; g_model.moduleData[0].channelsCount = DEFAULT_CHANNELS(INTERNAL_MODULE); + if (g_model.moduleData[INTERNAL_MODULE].rfProtocol == RF_PROTO_OFF) + g_model.moduleData[INTERNAL_MODULE].type = MODULE_TYPE_NONE; } + } break; @@ -641,7 +673,11 @@ case ITEM_MODEL_TRAINER_MODE: lcdDrawText(MENUS_MARGIN_LEFT, y, STR_MODE); - g_model.trainerMode = editChoice(MODEL_SETUP_2ND_COLUMN, y, STR_VTRAINERMODES, g_model.trainerMode, 0, HAS_WIRELESS_TRAINER_HARDWARE() ? TRAINER_MODE_MASTER_BATTERY_COMPARTMENT : TRAINER_MODE_SLAVE, attr, event); + g_model.trainerMode = editChoice(MODEL_SETUP_2ND_COLUMN, y, STR_VTRAINERMODES, g_model.trainerMode, 0, TRAINER_MODE_MAX(), attr, event); + if (attr && checkIncDec_Ret) { + bluetoothState = BLUETOOTH_STATE_OFF; + bluetoothDistantAddr[0] = 0; + } break; case ITEM_MODEL_EXTERNAL_MODULE_LABEL: @@ -655,6 +691,8 @@ lcdDrawTextAtIndex(MODEL_SETUP_3RD_COLUMN, y, STR_XJT_PROTOCOLS, 1+g_model.moduleData[EXTERNAL_MODULE].rfProtocol, (menuHorizontalPosition==1 ? attr : 0)); else if (IS_MODULE_DSM2(EXTERNAL_MODULE)) lcdDrawTextAtIndex(MODEL_SETUP_3RD_COLUMN, y, STR_DSM_PROTOCOLS, g_model.moduleData[EXTERNAL_MODULE].rfProtocol, (menuHorizontalPosition==1 ? attr : 0)); + else if (IS_MODULE_R9M(EXTERNAL_MODULE)) + lcdDrawTextAtIndex(MODEL_SETUP_3RD_COLUMN, y, STR_R9M_MODES, g_model.moduleData[EXTERNAL_MODULE].subType, (menuHorizontalPosition==1 ? attr : 0)); #if defined(MULTIMODULE) else if (IS_MODULE_MULTIMODULE(EXTERNAL_MODULE)) { int multi_rfProto = g_model.moduleData[EXTERNAL_MODULE].getMultiProtocol(false); @@ -662,9 +700,9 @@ lcdDrawText(MODEL_SETUP_3RD_COLUMN, y, STR_MULTI_CUSTOM, menuHorizontalPosition == 1 ? attr : 0); lcdDrawNumber(MODEL_SETUP_4TH_COLUMN, y, multi_rfProto, menuHorizontalPosition==2 ? attr : 0, 2); lcdDrawNumber(MODEL_SETUP_4TH_COLUMN + MODEL_SETUP_BIND_OFS, y, g_model.moduleData[EXTERNAL_MODULE].subType, menuHorizontalPosition==3 ? attr : 0, 2); - } else { - const mm_protocol_definition *pdef = getMultiProtocolDefinition(multi_rfProto); - + } + else { + const mm_protocol_definition * pdef = getMultiProtocolDefinition(multi_rfProto); lcdDrawTextAtIndex(MODEL_SETUP_3RD_COLUMN, y, STR_MULTI_PROTOCOLS, multi_rfProto, menuHorizontalPosition == 1 ? attr : 0); if (pdef->subTypeString != nullptr) lcdDrawTextAtIndex(MODEL_SETUP_4TH_COLUMN, y, pdef->subTypeString, g_model.moduleData[EXTERNAL_MODULE].subType, menuHorizontalPosition==2 ? attr : 0); @@ -679,11 +717,15 @@ g_model.moduleData[EXTERNAL_MODULE].rfProtocol = 0; g_model.moduleData[EXTERNAL_MODULE].channelsStart = 0; g_model.moduleData[EXTERNAL_MODULE].channelsCount = DEFAULT_CHANNELS(EXTERNAL_MODULE); + if (IS_MODULE_SBUS(EXTERNAL_MODULE)) + g_model.moduleData[EXTERNAL_MODULE].sbus.refreshRate = -31; } break; case 1: if (IS_MODULE_DSM2(EXTERNAL_MODULE)) CHECK_INCDEC_MODELVAR(event, g_model.moduleData[EXTERNAL_MODULE].rfProtocol, DSM2_PROTO_LP45, DSM2_PROTO_DSMX); + else if (IS_MODULE_R9M(EXTERNAL_MODULE)) + CHECK_INCDEC_MODELVAR(event, g_model.moduleData[EXTERNAL_MODULE].subType, MODULE_SUBTYPE_R9M_FCC, MODULE_SUBTYPE_R9M_LBT); #if defined(MULTIMODULE) else if (IS_MODULE_MULTIMODULE(EXTERNAL_MODULE)) { int multiRfProto = g_model.moduleData[EXTERNAL_MODULE].multi.customProto == 1 ? MM_RF_PROTO_CUSTOM : g_model.moduleData[EXTERNAL_MODULE].getMultiProtocol(false); @@ -696,7 +738,8 @@ // Sensible default for DSM2 (same as for ppm): 7ch@22ms + Autodetect settings enabled if (g_model.moduleData[EXTERNAL_MODULE].getMultiProtocol(true) == MM_RF_PROTO_DSM2) { g_model.moduleData[EXTERNAL_MODULE].multi.autoBindMode = 1; - } else { + } + else { g_model.moduleData[EXTERNAL_MODULE].multi.autoBindMode = 0; } g_model.moduleData[EXTERNAL_MODULE].multi.optionValue = 0; @@ -736,9 +779,49 @@ lcdDrawText(MENUS_MARGIN_LEFT, y, STR_TRAINER); break; + case ITEM_MODEL_TRAINER_LINE1: + if (g_model.trainerMode == TRAINER_MODE_MASTER_BLUETOOTH) { + if (attr) { + s_editMode = 0; + } + if (bluetoothDistantAddr[0]) { + lcdDrawText(MENUS_MARGIN_LEFT + INDENT_WIDTH, y, bluetoothDistantAddr); + if (bluetoothState != BLUETOOTH_STATE_CONNECTED) { + drawButton(MODEL_SETUP_2ND_COLUMN, y, "Bind", menuHorizontalPosition == 0 ? attr : 0); + drawButton(MODEL_SETUP_2ND_COLUMN+60, y, "Clear", menuHorizontalPosition == 1 ? attr : 0); + } + else { + drawButton(MODEL_SETUP_2ND_COLUMN, y, "Clear", attr); + } + if (attr && event == EVT_KEY_FIRST(KEY_ENTER)) { + if (bluetoothState == BLUETOOTH_STATE_CONNECTED || menuHorizontalPosition == 1) { + bluetoothState = BLUETOOTH_STATE_OFF; + bluetoothDistantAddr[0] = 0; + } + else { + bluetoothState = BLUETOOTH_STATE_BIND_REQUESTED; + } + } + } + else { + lcdDrawText(MENUS_MARGIN_LEFT + INDENT_WIDTH, y, "---"); + if (bluetoothState < BLUETOOTH_STATE_IDLE) + drawButton(MODEL_SETUP_2ND_COLUMN, y, "Init", attr); + else + drawButton(MODEL_SETUP_2ND_COLUMN, y, "Discover", attr); + if (attr && event == EVT_KEY_FIRST(KEY_ENTER)) { + if (bluetoothState < BLUETOOTH_STATE_IDLE) + bluetoothState = BLUETOOTH_STATE_OFF; + else + bluetoothState = BLUETOOTH_STATE_DISCOVER_REQUESTED; + } + } + break; + } + // no break + case ITEM_MODEL_INTERNAL_MODULE_CHANNELS: case ITEM_MODEL_EXTERNAL_MODULE_CHANNELS: - case ITEM_MODEL_TRAINER_CHANNELS: { uint8_t moduleIdx = CURRENT_MODULE_EDITED(k); ModuleData & moduleData = g_model.moduleData[moduleIdx]; @@ -747,11 +830,11 @@ drawStringWithIndex(MODEL_SETUP_2ND_COLUMN, y, STR_CH, moduleData.channelsStart+1, menuHorizontalPosition==0 ? attr : 0); lcdDrawText(lcdNextPos+5, y, "-"); drawStringWithIndex(lcdNextPos+5, y, STR_CH, moduleData.channelsStart+NUM_CHANNELS(moduleIdx), menuHorizontalPosition==1 ? attr : 0); - if (IS_MODULE_XJT(moduleIdx) && g_model.moduleData[moduleIdx].rfProtocol== RF_PROTO_X16) { + if (IS_R9M_OR_XJTD16(moduleIdx)) { if (NUM_CHANNELS(moduleIdx) > 8) - lcdDrawText(lcdNextPos+15, y, "(18ms)"); + lcdDrawText(lcdNextPos + 15, y, "(18ms)"); else - lcdDrawText(lcdNextPos+15, y, "(9ms)"); + lcdDrawText(lcdNextPos + 15, y, "(9ms)"); } if (attr && s_editMode>0) { switch (menuHorizontalPosition) { @@ -761,7 +844,7 @@ case 1: CHECK_INCDEC_MODELVAR(event, moduleData.channelsCount, -4, min(MAX_CHANNELS(moduleIdx), 32-8-moduleData.channelsStart)); if ((k == ITEM_MODEL_EXTERNAL_MODULE_CHANNELS && g_model.moduleData[EXTERNAL_MODULE].type == MODULE_TYPE_PPM) - || (k == ITEM_MODEL_TRAINER_CHANNELS) + || (k == ITEM_MODEL_TRAINER_LINE1) ) SET_DEFAULT_PPM_FRAME_LENGTH(moduleIdx); break; @@ -773,7 +856,7 @@ case ITEM_MODEL_INTERNAL_MODULE_BIND: case ITEM_MODEL_EXTERNAL_MODULE_BIND: - case ITEM_MODEL_TRAINER_SETTINGS: + case ITEM_MODEL_TRAINER_LINE2: { uint8_t moduleIdx = CURRENT_MODULE_EDITED(k); ModuleData & moduleData = g_model.moduleData[moduleIdx]; @@ -796,6 +879,22 @@ } } } + else if (IS_MODULE_SBUS(moduleIdx)) { + lcdDrawText(MENUS_MARGIN_LEFT, y, STR_REFRESHRATE); + lcdDrawNumber(MODEL_SETUP_2ND_COLUMN, y, (int16_t)moduleData.ppm.frameLength*5 + 225, (menuHorizontalPosition<=0 ? attr : 0) | PREC1|LEFT, 0, NULL, STR_MS); + lcdDrawText(MODEL_SETUP_3RD_COLUMN, y, moduleData.sbus.noninverted ? "not inverted" : "normal", (CURSOR_ON_LINE() || menuHorizontalPosition==1) ? attr : 0); + + if (attr && s_editMode>0) { + switch (menuHorizontalPosition) { + case 0: + CHECK_INCDEC_MODELVAR(event, moduleData.ppm.frameLength, -33, 35); + break; + case 1: + CHECK_INCDEC_MODELVAR_ZERO(event, moduleData.sbus.noninverted, 1); + break; + } + } + } else { int l_posHorz = menuHorizontalPosition; coord_t xOffsetBind = MODEL_SETUP_BIND_OFS; @@ -807,40 +906,53 @@ else { lcdDrawText(MENUS_MARGIN_LEFT, y, STR_RECEIVER_NUM); } - if (IS_MODULE_XJT(moduleIdx) || IS_MODULE_DSM2(moduleIdx) || IS_MODULE_MULTIMODULE(moduleIdx)) { - if (xOffsetBind) lcdDrawNumber(MODEL_SETUP_2ND_COLUMN, y, g_model.header.modelId[moduleIdx], (l_posHorz==0 ? attr : 0) | LEADING0 | LEFT, 2); - if (attr && l_posHorz==0 && s_editMode>0) { + if (IS_MODULE_PXX(moduleIdx) || IS_MODULE_DSM2(moduleIdx) || IS_MODULE_MULTIMODULE(moduleIdx)) { + if (xOffsetBind) + lcdDrawNumber(MODEL_SETUP_2ND_COLUMN, y, g_model.header.modelId[moduleIdx], (l_posHorz==0 ? attr : 0) | LEADING0 | LEFT, 2); + if (attr && l_posHorz==0 && s_editMode>0) CHECK_INCDEC_MODELVAR_ZERO(event, g_model.header.modelId[moduleIdx], MAX_RX_NUM(moduleIdx)); - } drawButton(MODEL_SETUP_2ND_COLUMN+xOffsetBind, y, STR_MODULE_BIND, (moduleFlag[moduleIdx] == MODULE_BIND ? BUTTON_ON : BUTTON_OFF) | (l_posHorz==1 ? attr : 0)); drawButton(MODEL_SETUP_2ND_COLUMN+MODEL_SETUP_RANGE_OFS+xOffsetBind, y, STR_MODULE_RANGE, (moduleFlag[moduleIdx] == MODULE_RANGECHECK ? BUTTON_ON : BUTTON_OFF) | (l_posHorz==2 ? attr : 0)); uint8_t newFlag = 0; #if defined(MULTIMODULE) if (multiBindStatus == MULTI_BIND_FINISHED) { multiBindStatus = MULTI_NORMAL_OPERATION; - s_editMode=0; + s_editMode = 0; } #endif -#if defined(BINDING_OPTIONS) if (attr && l_posHorz>0) { - if(s_editMode>0) { + if (s_editMode>0) { if (l_posHorz == 1) { - if (IS_MODULE_XJT(moduleIdx) && g_model.moduleData[moduleIdx].rfProtocol== RF_PROTO_X16 && s_current_protocol[INTERNAL_MODULE] == PROTO_PXX) { - if(event==EVT_KEY_BREAK(KEY_ENTER)) { - POPUP_MENU_ADD_ITEM(STR_BINDING_1_8_TELEM_ON); - POPUP_MENU_ADD_ITEM(STR_BINDING_1_8_TELEM_OFF); - POPUP_MENU_ADD_ITEM(STR_BINDING_9_16_TELEM_ON); - POPUP_MENU_ADD_ITEM(STR_BINDING_9_16_TELEM_OFF); - POPUP_MENU_SELECT_ITEM(g_model.moduleData[INTERNAL_MODULE].pxx.receiver_telem_off + (g_model.moduleData[INTERNAL_MODULE].pxx.receiver_channel_9_16 << 1)); + if (IS_MODULE_R9M(moduleIdx) || (IS_MODULE_XJT(moduleIdx) && g_model.moduleData[moduleIdx].rfProtocol == RF_PROTO_X16)) { + if (event == EVT_KEY_BREAK(KEY_ENTER)) { + uint8_t default_selection; + if (IS_MODULE_R9M_LBT(moduleIdx)) { + if (!IS_TELEMETRY_INTERNAL_MODULE()) + POPUP_MENU_ADD_ITEM(STR_BINDING_25MW_CH1_8_TELEM_ON); + POPUP_MENU_ADD_ITEM(STR_BINDING_25MW_CH1_8_TELEM_OFF); + POPUP_MENU_ADD_ITEM(STR_BINDING_500MW_CH1_8_TELEM_OFF); + POPUP_MENU_ADD_ITEM(STR_BINDING_500MW_CH9_16_TELEM_OFF); + default_selection = 2; + } + else { + if (!(IS_TELEMETRY_INTERNAL_MODULE() && moduleIdx == EXTERNAL_MODULE)) + POPUP_MENU_ADD_ITEM(STR_BINDING_1_8_TELEM_ON); + POPUP_MENU_ADD_ITEM(STR_BINDING_1_8_TELEM_OFF); + if (!(IS_TELEMETRY_INTERNAL_MODULE() && moduleIdx == EXTERNAL_MODULE)) + POPUP_MENU_ADD_ITEM(STR_BINDING_9_16_TELEM_ON); + POPUP_MENU_ADD_ITEM(STR_BINDING_9_16_TELEM_OFF); + default_selection = g_model.moduleData[moduleIdx].pxx.receiver_telem_off + (g_model.moduleData[moduleIdx].pxx.receiver_channel_9_16 << 1); + } + POPUP_MENU_SELECT_ITEM(default_selection); POPUP_MENU_START(onBindMenu); continue; } - if (moduleFlag[INTERNAL_MODULE] == MODULE_BIND) { + if (moduleFlag[moduleIdx] == MODULE_BIND) { newFlag = MODULE_BIND; } else { if (!popupMenuNoItems) { - s_editMode=0; // this is when popup is exited before a choice is made + s_editMode = 0; // this is when popup is exited before a choice is made } } } @@ -851,13 +963,6 @@ else if (l_posHorz == 2) { newFlag = MODULE_RANGECHECK; } -#else - if (attr && l_posHorz>0 && s_editMode>0) { - if (l_posHorz == 1) - newFlag = MODULE_BIND; - else if (l_posHorz == 2) { - newFlag = MODULE_RANGECHECK; -#endif } } moduleFlag[moduleIdx] = newFlag; @@ -874,40 +979,44 @@ case ITEM_MODEL_EXTERNAL_MODULE_FAILSAFE: { uint8_t moduleIdx = CURRENT_MODULE_EDITED(k); - if (IS_MODULE_XJT(moduleIdx)) { ModuleData & moduleData = g_model.moduleData[moduleIdx]; lcdDrawText(MENUS_MARGIN_LEFT, y, STR_FAILSAFE); - lcdDrawTextAtIndex(MODEL_SETUP_2ND_COLUMN, y, STR_VFAILSAFE, moduleData.failsafeMode, menuHorizontalPosition==0 ? attr : 0); - if (moduleData.failsafeMode == FAILSAFE_CUSTOM) { - drawButton(MODEL_SETUP_2ND_COLUMN + MODEL_SETUP_SET_FAILSAFE_OFS, y, STR_SET, menuHorizontalPosition==1 ? attr : 0); - } - if (attr) { - if (moduleData.failsafeMode != FAILSAFE_CUSTOM) - menuHorizontalPosition = 0; - if (menuHorizontalPosition==0) { - if (s_editMode>0) { - CHECK_INCDEC_MODELVAR_ZERO(event, moduleData.failsafeMode, FAILSAFE_LAST); - if (checkIncDec_Ret) SEND_FAILSAFE_NOW(moduleIdx); - } - } - else if (menuHorizontalPosition==1) { - s_editMode = 0; - if (moduleData.failsafeMode==FAILSAFE_CUSTOM && event==EVT_KEY_FIRST(KEY_ENTER)) { - g_moduleIdx = moduleIdx; - pushMenu(menuModelFailsafe); - } + lcdDrawTextAtIndex(MODEL_SETUP_2ND_COLUMN, y, STR_VFAILSAFE, moduleData.failsafeMode, menuHorizontalPosition==0 ? attr : 0); + if (moduleData.failsafeMode == FAILSAFE_CUSTOM) { + drawButton(MODEL_SETUP_2ND_COLUMN + MODEL_SETUP_SET_FAILSAFE_OFS, y, STR_SET, menuHorizontalPosition==1 ? attr : 0); + } + if (attr) { + if (moduleData.failsafeMode != FAILSAFE_CUSTOM) + menuHorizontalPosition = 0; + if (menuHorizontalPosition==0) { + if (s_editMode>0) { + CHECK_INCDEC_MODELVAR_ZERO(event, moduleData.failsafeMode, FAILSAFE_LAST); + if (checkIncDec_Ret) SEND_FAILSAFE_NOW(moduleIdx); } - else { - lcdDrawSolidFilledRect(MODEL_SETUP_2ND_COLUMN, y, LCD_W-MODEL_SETUP_2ND_COLUMN-2, 8, TEXT_COLOR); + } + else if (menuHorizontalPosition==1) { + s_editMode = 0; + if (moduleData.failsafeMode==FAILSAFE_CUSTOM && event==EVT_KEY_FIRST(KEY_ENTER)) { + g_moduleIdx = moduleIdx; + pushMenu(menuModelFailsafe); } } + else { + lcdDrawSolidFilledRect(MODEL_SETUP_2ND_COLUMN, y, LCD_W - MODEL_SETUP_2ND_COLUMN - 2, 8, TEXT_COLOR); + } } + break; + } + + case ITEM_MODEL_EXTERNAL_MODULE_OPTIONS: + { + uint8_t moduleIdx = CURRENT_MODULE_EDITED(k); #if defined(MULTIMODULE) - else if (IS_MODULE_MULTIMODULE(moduleIdx)) { - int optionValue = g_model.moduleData[moduleIdx].multi.optionValue; + if (IS_MODULE_MULTIMODULE(moduleIdx)) { + int optionValue = g_model.moduleData[moduleIdx].multi.optionValue; const uint8_t multi_proto = g_model.moduleData[EXTERNAL_MODULE].getMultiProtocol(true); - const mm_protocol_definition* pdef = getMultiProtocolDefinition(multi_proto); + const mm_protocol_definition *pdef = getMultiProtocolDefinition(multi_proto); if (pdef->optionsstr) lcdDrawText(MENUS_MARGIN_LEFT, y, pdef->optionsstr); @@ -918,16 +1027,62 @@ if (attr) { if (multi_proto == MM_RF_PROTO_FS_AFHDS2A) { CHECK_INCDEC_MODELVAR(event, g_model.moduleData[moduleIdx].multi.optionValue, 0, 70); - } else if (multi_proto == MM_RF_PROTO_OLRS) { + } + else if (multi_proto == MM_RF_PROTO_OLRS) { CHECK_INCDEC_MODELVAR(event, g_model.moduleData[moduleIdx].multi.optionValue, -1, 7); - } else { + } + else { CHECK_INCDEC_MODELVAR(event, g_model.moduleData[moduleIdx].multi.optionValue, -128, 127); } } } #endif - break; + if (IS_MODULE_R9M_FCC(moduleIdx)) { + if (IS_TELEMETRY_INTERNAL_MODULE()) { + lcdDrawText(MENUS_MARGIN_LEFT, y, STR_MODULE_TELEMETRY); + lcdDrawText(MODEL_SETUP_2ND_COLUMN, y, STR_DISABLE_INTERNAL); + } + else { + lcdDrawText(MENUS_MARGIN_LEFT, y, STR_MODULE_TELEMETRY); + g_model.moduleData[moduleIdx].pxx.sport_out = editCheckBox(g_model.moduleData[EXTERNAL_MODULE].pxx.sport_out, MODEL_SETUP_2ND_COLUMN, y, attr, event); + } + } + else if (IS_MODULE_R9M_LBT(moduleIdx)) { + if (IS_TELEMETRY_INTERNAL_MODULE()) { + lcdDrawText(MENUS_MARGIN_LEFT, y, STR_MODULE_TELEMETRY); + lcdDrawText(MODEL_SETUP_2ND_COLUMN, y, STR_DISABLE_INTERNAL); + } + else { + lcdDrawText(MENUS_MARGIN_LEFT,y, STR_MODULE_TELEMETRY); + lcdDrawText(MODEL_SETUP_2ND_COLUMN, y, STR_BINDING_OPTION); + } + } + else if (IS_MODULE_SBUS(moduleIdx)) { + lcdDrawText(MENUS_MARGIN_LEFT, y, STR_WARN_BATTVOLTAGE); + drawValueWithUnit(MODEL_SETUP_4TH_COLUMN, y, getBatteryVoltage(), UNIT_VOLTS, attr|PREC2|LEFT); + } + } + break; + + case ITEM_MODEL_EXTERNAL_MODULE_POWER: + { + uint8_t moduleIdx = CURRENT_MODULE_EDITED(k); + if (IS_MODULE_R9M_FCC(moduleIdx)) { + // Power selection is only available on R9M FCC + lcdDrawText(MENUS_MARGIN_LEFT, y, STR_MULTI_RFPOWER); + lcdDrawTextAtIndex(MODEL_SETUP_2ND_COLUMN, y, STR_R9M_FCC_POWER_VALUES, g_model.moduleData[moduleIdx].pxx.power, LEFT | attr); + if (attr) + CHECK_INCDEC_MODELVAR(event, g_model.moduleData[moduleIdx].pxx.power, 0, R9M_FCC_POWER_MAX); + } +#if defined(MULTIMODULE) + else if (IS_MODULE_MULTIMODULE(moduleIdx)) { + lcdDrawText(MENUS_MARGIN_LEFT, y, STR_MULTI_LOWPOWER); + g_model.moduleData[EXTERNAL_MODULE].multi.lowPowerMode = editCheckBox(g_model.moduleData[EXTERNAL_MODULE].multi.lowPowerMode, MODEL_SETUP_2ND_COLUMN, y, attr, event); + } +#endif } + break; + #if defined(MULTIMODULE) case ITEM_MODEL_EXTERNAL_MODULE_AUTOBIND: if (g_model.moduleData[EXTERNAL_MODULE].getMultiProtocol(true) == MM_RF_PROTO_DSM2) @@ -936,10 +1091,6 @@ lcdDrawText(MENUS_MARGIN_LEFT, y, STR_MULTI_AUTOBIND); g_model.moduleData[EXTERNAL_MODULE].multi.autoBindMode = editCheckBox(g_model.moduleData[EXTERNAL_MODULE].multi.autoBindMode, MODEL_SETUP_2ND_COLUMN, y, attr, event); break; - case ITEM_MODEL_EXTERNAL_MODULE_LOWPOWER: - lcdDrawText(MENUS_MARGIN_LEFT, y, STR_MULTI_LOWPOWER); - g_model.moduleData[EXTERNAL_MODULE].multi.lowPowerMode = editCheckBox(g_model.moduleData[EXTERNAL_MODULE].multi.lowPowerMode, MODEL_SETUP_2ND_COLUMN, y, attr, event); - break; case ITEM_MODEL_EXTERNAL_MODULE_STATUS: { lcdDrawText(MENUS_MARGIN_LEFT, y, STR_MODULE_STATUS); @@ -947,6 +1098,14 @@ multiModuleStatus.getStatusString(statusText); lcdDrawText(MODEL_SETUP_2ND_COLUMN, y, statusText); break; + case ITEM_MODEL_EXTERNAL_MODULE_SYNCSTATUS: { + lcdDrawText(MENUS_MARGIN_LEFT, y, STR_MODULE_SYNC); + + char statusText[64]; + multiSyncStatus.getRefreshString(statusText); + lcdDrawText(MODEL_SETUP_2ND_COLUMN, y, statusText); + break; + } } #endif } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/model_special_functions.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/model_special_functions.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/model_special_functions.cpp 2017-04-29 16:57:04.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/model_special_functions.cpp 2017-11-15 20:54:40.000000000 +0000 @@ -182,7 +182,7 @@ case ITEM_SPECIAL_FUNCTIONS_SWITCH: drawSwitch(MODEL_SPECIAL_FUNC_1ST_COLUMN, y, CFN_SWITCH(cfn), attr | ((functionsContext.activeSwitches & ((MASK_CFN_TYPE)1 << k)) ? BOLD : 0)); if (active || AUTOSWITCH_ENTER_LONG()) { - CHECK_INCDEC_SWITCH(event, CFN_SWITCH(cfn), SWSRC_FIRST, functions == g_eeGeneral.customFn ? SWSRC_TELEMETRY_STREAMING : SWSRC_LAST, eeFlags, isSwitchAvailableInCustomFunctions); + CHECK_INCDEC_SWITCH(event, CFN_SWITCH(cfn), SWSRC_FIRST, SWSRC_LAST, eeFlags, isSwitchAvailableInCustomFunctions); } if (func == FUNC_OVERRIDE_CHANNEL && functions != g_model.customFn) { func = CFN_FUNC(cfn) = func+1; @@ -340,10 +340,14 @@ else if (func == FUNC_ADJUST_GVAR) { switch (CFN_GVAR_MODE(cfn)) { case FUNC_ADJUST_GVAR_CONSTANT: - val_displayed = (int16_t)CFN_PARAM(cfn); - val_min = -CFN_GVAR_CST_MAX; val_max = +CFN_GVAR_CST_MAX; - lcdDrawNumber(MODEL_SPECIAL_FUNC_3RD_COLUMN, y, val_displayed, attr|LEFT); + { + uint8_t gvar_index = CFN_GVAR_INDEX(cfn); + val_displayed = (int16_t) CFN_PARAM(cfn); + val_min = max(CFN_GVAR_CST_MIN, MODEL_GVAR_MIN(gvar_index)); + val_max = min(CFN_GVAR_CST_MAX, MODEL_GVAR_MAX(gvar_index)); + drawGVarValue(MODEL_SPECIAL_FUNC_3RD_COLUMN, y, gvar_index, val_displayed, attr|LEFT); break; + } case FUNC_ADJUST_GVAR_SOURCE: val_max = MIXSRC_LAST_CH; drawSource(MODEL_SPECIAL_FUNC_3RD_COLUMN, y, val_displayed, attr); @@ -362,7 +366,7 @@ lcdDrawText(MODEL_SPECIAL_FUNC_3RD_COLUMN, y, "-= ", attr); else lcdDrawText(MODEL_SPECIAL_FUNC_3RD_COLUMN, y, "+= ", attr); - lcdDrawNumber(lcdNextPos, y, abs(val_displayed), attr|LEFT); + drawGVarValue(lcdNextPos, y, CFN_GVAR_INDEX(cfn), abs(val_displayed), attr|LEFT); break; } } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/model_telemetry.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/model_telemetry.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/model_telemetry.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/model_telemetry.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -25,6 +25,7 @@ ITEM_TELEMETRY_RSSI_LABEL, ITEM_TELEMETRY_RSSI_ALARM1, ITEM_TELEMETRY_RSSI_ALARM2, + ITEM_TELEMETRY_DISABLE_ALARMS, ITEM_TELEMETRY_SENSORS_LABEL, ITEM_TELEMETRY_SENSOR1, ITEM_TELEMETRY_SENSOR2, @@ -87,7 +88,7 @@ #else #define VARIO_ROWS #endif -#define RSSI_ROWS LABEL(RSSI), 0, 0, +#define RSSI_ROWS LABEL(RSSI), 0, 0, 0, #define VARIO_RANGE_ROWS 3 #define TELEMETRY_TYPE_ROWS (g_model.moduleData[INTERNAL_MODULE].rfProtocol == RF_PROTO_OFF && g_model.moduleData[EXTERNAL_MODULE].type == MODULE_TYPE_PPM) ? (uint8_t)0 : HIDDEN_ROW, @@ -533,15 +534,22 @@ case ITEM_TELEMETRY_RSSI_ALARM1: case ITEM_TELEMETRY_RSSI_ALARM2: { - uint8_t alarm = k-ITEM_TELEMETRY_RSSI_ALARM1; - lcdDrawText(MENUS_MARGIN_LEFT, y, (alarm==0 ? STR_LOWALARM : STR_CRITICALALARM)); - lcdDrawNumber(TELEM_COL2, y, getRssiAlarmValue(alarm), LEFT|attr, 3); + bool warning = (k==ITEM_TELEMETRY_RSSI_ALARM1); + lcdDrawText(MENUS_MARGIN_LEFT, y, (warning ? STR_LOWALARM : STR_CRITICALALARM)); + lcdDrawNumber(TELEM_COL2, y, warning? g_model.rssiAlarms.getWarningRssi() : g_model.rssiAlarms.getCriticalRssi(), LEFT|attr, 3); + if (attr && s_editMode>0) { - CHECK_INCDEC_MODELVAR(event, g_model.frsky.rssiAlarms[alarm].value, -30, 30); + if (warning) + CHECK_INCDEC_MODELVAR(event, g_model.rssiAlarms.warning, -30, 30); + else + CHECK_INCDEC_MODELVAR(event, g_model.rssiAlarms.critical, -30, 30); } break; } - + case ITEM_TELEMETRY_DISABLE_ALARMS: + lcdDrawText(MENUS_MARGIN_LEFT, y, STR_DISABLE_ALARM); + g_model.rssiAlarms.disabled = editCheckBox(g_model.rssiAlarms.disabled, TELEM_COL3, y, attr, event); + break; #if defined(VARIO) case ITEM_TELEMETRY_VARIO_LABEL: lcdDrawText(MENUS_MARGIN_LEFT, y, STR_VARIO); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/popups.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/popups.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/popups.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/popups.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -65,6 +65,8 @@ lcdRefresh(); lcdSetContrast(); clearKeyEvents(); + backlightOn(); + checkBacklight(); } void showMessageBox(const char * title) diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/radio_hardware.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/radio_hardware.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/radio_hardware.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/radio_hardware.cpp 2017-11-10 17:23:25.000000000 +0000 @@ -46,7 +46,9 @@ ITEM_RADIO_HARDWARE_SF, ITEM_RADIO_HARDWARE_SG, ITEM_RADIO_HARDWARE_SH, - ITEM_RADIO_HARDWARE_BLUETOOTH, + CASE_PCBX10(ITEM_RADIO_HARDWARE_SERIAL_BAUDRATE) + ITEM_RADIO_HARDWARE_BLUETOOTH_MODE, + ITEM_RADIO_HARDWARE_BLUETOOTH_NAME, #if defined(SERIAL2) && defined(DEBUG) ITEM_RADIO_HARDWARE_UART3_MODE, #endif @@ -62,12 +64,12 @@ #define POTS_ROWS NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1 #endif #define SWITCHES_ROWS NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1, NAVIGATION_LINE_BY_LINE|1 -#define BLUETOOTH_ROWS 1, +#define BLUETOOTH_ROWS 0, uint8_t(g_eeGeneral.bluetoothMode == BLUETOOTH_OFF ? -1 : 0) #define SWITCH_TYPE_MAX(sw) ((MIXSRC_SF-MIXSRC_FIRST_SWITCH == sw || MIXSRC_SH-MIXSRC_FIRST_SWITCH == sw) ? SWITCH_2POS : SWITCH_3POS) bool menuRadioHardware(event_t event) { - MENU(STR_HARDWARE, RADIO_ICONS, menuTabGeneral, MENU_RADIO_HARDWARE, ITEM_RADIO_HARDWARE_MAX, { 0, LABEL(Sticks), 0, 0, 0, 0, LABEL(Pots), POTS_ROWS, LABEL(Switches), SWITCHES_ROWS, BLUETOOTH_ROWS 0, 0, 0 }); + MENU(STR_HARDWARE, RADIO_ICONS, menuTabGeneral, MENU_RADIO_HARDWARE, ITEM_RADIO_HARDWARE_MAX, { 0, LABEL(Sticks), 0, 0, 0, 0, LABEL(Pots), POTS_ROWS, LABEL(Switches), SWITCHES_ROWS, CASE_PCBX10(0) BLUETOOTH_ROWS, 0, 0, 0 }); uint8_t sub = menuVerticalPosition; @@ -167,13 +169,34 @@ break; } - case ITEM_RADIO_HARDWARE_BLUETOOTH: - lcdDrawText(MENUS_MARGIN_LEFT, y, "Bluetooth"); - drawCheckBox(HW_SETTINGS_COLUMN, y, g_eeGeneral.bluetoothEnable, menuHorizontalPosition == 0 ? attr : 0); - if (attr && menuHorizontalPosition == 0) { - g_eeGeneral.bluetoothEnable = checkIncDecGen(event, g_eeGeneral.bluetoothEnable, 0, 1); +#if defined (PCBX10) + case ITEM_RADIO_HARDWARE_SERIAL_BAUDRATE: + lcdDrawText(MENUS_MARGIN_LEFT, y, STR_MAXBAUDRATE); + lcdDrawNumber(HW_SETTINGS_COLUMN+50, y, CROSSFIRE_BAUDRATES[g_eeGeneral.telemetryBaudrate], attr|LEFT); + if (attr) { + g_eeGeneral.telemetryBaudrate = DIM(CROSSFIRE_BAUDRATES) - 1 - checkIncDecModel(event, DIM(CROSSFIRE_BAUDRATES) - 1 - g_eeGeneral.telemetryBaudrate, 0, DIM(CROSSFIRE_BAUDRATES) - 1); + if (checkIncDec_Ret) { + pauseMixerCalculations(); + pausePulses(); + EXTERNAL_MODULE_OFF(); + CoTickDelay(10); // 20ms so that the pulses interrupt will reinit the frame rate + telemetryProtocol = 255; // force telemetry port + module reinitialization + EXTERNAL_MODULE_ON(); + resumePulses(); + resumeMixerCalculations(); + } } - editName(HW_SETTINGS_COLUMN+50, y, g_eeGeneral.bluetoothName, LEN_BLUETOOTH_NAME, event, menuHorizontalPosition == 1 ? attr : 0); + break; +#endif + + case ITEM_RADIO_HARDWARE_BLUETOOTH_MODE: + lcdDrawText(MENUS_MARGIN_LEFT, y, STR_BLUETOOTH); + g_eeGeneral.bluetoothMode = editChoice(HW_SETTINGS_COLUMN+50, y, STR_BLUETOOTH_MODES, g_eeGeneral.bluetoothMode, BLUETOOTH_OFF, BLUETOOTH_TRAINER, attr, event); + break; + + case ITEM_RADIO_HARDWARE_BLUETOOTH_NAME: + lcdDrawText(INDENT_WIDTH, y, STR_NAME); + editName(HW_SETTINGS_COLUMN+50, y, g_eeGeneral.bluetoothName, LEN_BLUETOOTH_NAME, event, attr); break; #if defined(SERIAL2) && defined(DEBUG) @@ -190,13 +213,13 @@ { lcdDrawText(MENUS_MARGIN_LEFT, y, STR_JITTER_FILTER); uint8_t b = 1-g_eeGeneral.jitterFilter; - g_eeGeneral.jitterFilter = 1 - editCheckBox(b, HW_SETTINGS_COLUMN, y, attr, event); + g_eeGeneral.jitterFilter = 1 - editCheckBox(b, HW_SETTINGS_COLUMN+50, y, attr, event); break; } case ITEM_RADIO_HARDWARE_BAT_CAL: lcdDrawText(MENUS_MARGIN_LEFT, y, STR_BATT_CALIB); - lcdDrawNumber(HW_SETTINGS_COLUMN, y, getBatteryVoltage(), attr|LEFT|PREC2, 0, NULL, "V"); + lcdDrawNumber(HW_SETTINGS_COLUMN+50, y, getBatteryVoltage(), attr|LEFT|PREC2, 0, NULL, "V"); if (attr) CHECK_INCDEC_GENVAR(event, g_eeGeneral.txVoltageCalibration, -127, 127); break; } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/radio_sdmanager.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/radio_sdmanager.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/radio_sdmanager.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/radio_sdmanager.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -151,14 +151,10 @@ showMessageBox(STR_FORMATTING); logsClose(); audioQueue.stopSD(); - BYTE work[_MAX_SS]; - if (f_mkfs(0, FM_FAT32, 0, work, sizeof(work)) == FR_OK) { + if(sdCardFormat()) { f_chdir("/"); REFRESH_FILES(); } - else { - POPUP_WARNING(STR_SDCARD_ERROR); - } } event_t event = (EVT_KEY_MASK(_event) == KEY_ENTER ? 0 : _event); @@ -279,6 +275,7 @@ res = sdReadDir(&dir, &fno, firstTime); if (res != FR_OK || fno.fname[0] == 0) break; /* Break on error or end of dir */ if (strlen(fno.fname) > SD_SCREEN_FILE_LENGTH) continue; + if (fno.fname[0] == '.' && fno.fname[1] != '.') continue; /* Ignore hidden files under UNIX, but not .. */ reusableBuffer.sdmanager.count++; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/radio_setup.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/radio_setup.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/radio_setup.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/radio_setup.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -22,7 +22,7 @@ #include "opentx.h" -#define RADIO_SETUP_2ND_COLUMN 220 +#define RADIO_SETUP_2ND_COLUMN 235 int8_t editSlider(coord_t x, coord_t y, event_t event, int8_t value, int8_t min, int8_t max, LcdFlags attr) { @@ -59,6 +59,7 @@ ITEM_SETUP_INACTIVITY_ALARM, // ITEM_SETUP_MEMORY_WARNING, ITEM_SETUP_ALARM_WARNING, + ITEM_SETUP_RSSI_POWEROFF_ALARM, ITEM_SETUP_BACKLIGHT_LABEL, ITEM_SETUP_BACKLIGHT_MODE, ITEM_SETUP_BACKLIGHT_DELAY, @@ -72,9 +73,10 @@ CASE_PXX(ITEM_SETUP_COUNTRYCODE) ITEM_SETUP_LANGUAGE, ITEM_SETUP_IMPERIAL, - // IF_FAI_CHOICE(ITEM_SETUP_FAI) + IF_FAI_CHOICE(ITEM_SETUP_FAI) // CASE_MAVLINK(ITEM_MAVLINK_BAUD) ITEM_SETUP_SWITCHES_DELAY, + ITEM_SETUP_USB_MODE, ITEM_SETUP_RX_CHANNEL_ORD, ITEM_SETUP_STICK_MODE, ITEM_SETUP_MAX @@ -95,22 +97,26 @@ #endif #if defined(FAI_CHOICE) + #define FAI_CHOICE_ROW (g_eeGeneral.fai ? (uint8_t)-1 : (uint8_t)0), + if (warningResult) { warningResult = 0; g_eeGeneral.fai = true; storageDirty(EE_GENERAL); } +#else + #define FAI_CHOICE_ROW #endif MENU(STR_MENURADIOSETUP, RADIO_ICONS, menuTabGeneral, MENU_RADIO_SETUP, ITEM_SETUP_MAX, { - 2|NAVIGATION_LINE_BY_LINE, 2|NAVIGATION_LINE_BY_LINE, 1|NAVIGATION_LINE_BY_LINE, + 2|NAVIGATION_LINE_BY_LINE, 2|NAVIGATION_LINE_BY_LINE, 1|NAVIGATION_LINE_BY_LINE, // Date Time Bat range LABEL(SOUND), 0, 0, 0, 0, 0, 0, 0, CASE_VARIO(LABEL(VARIO)) CASE_VARIO(0) CASE_VARIO(0) CASE_VARIO(0) CASE_VARIO(0) CASE_HAPTIC(LABEL(HAPTIC)) CASE_HAPTIC(0) CASE_HAPTIC(0) CASE_HAPTIC(0) - LABEL(ALARMS), 0, 0, 0, + LABEL(ALARMS), 0, 0, 0, 0, LABEL(BACKLIGHT), 0, 0, 0, 0, 0, CASE_GPS(LABEL(GPS)) CASE_GPS(0) CASE_GPS(0) CASE_GPS(0) - CASE_PXX(0) 0, 0, 0, 0, 0, 0, 1/*to force edit mode*/ }); + CASE_PXX(0) 0, 0, FAI_CHOICE_ROW 0, 0, 0, 0, 1/*to force edit mode*/ }); // Country code - Voice Language - Units - Fai choice - Play delay - USB mode - Chan order - Mode (1 to 4) if (event == EVT_ENTRY) { reusableBuffer.generalSettings.stickMode = g_eeGeneral.stickMode; @@ -326,21 +332,19 @@ if (attr) CHECK_INCDEC_GENVAR(event, g_eeGeneral.vBatWarn, 40, 120); //4-12V break; -#if 0 - case ITEM_SETUP_MEMORY_WARNING: + case ITEM_SETUP_ALARM_WARNING: { - lcdDrawText(MENUS_MARGIN_LEFT, y, STR_MEMORYWARNING); - uint8_t b = 1-g_eeGeneral.disableMemoryWarning; - g_eeGeneral.disableMemoryWarning = 1 - editCheckBox(b, RADIO_SETUP_2ND_COLUMN, y, attr, event); + lcdDrawText(MENUS_MARGIN_LEFT, y, STR_ALARMWARNING); + uint8_t b = 1 - g_eeGeneral.disableAlarmWarning; + g_eeGeneral.disableAlarmWarning = 1 - editCheckBox(b, RADIO_SETUP_2ND_COLUMN, y, attr, event); break; } -#endif - case ITEM_SETUP_ALARM_WARNING: + case ITEM_SETUP_RSSI_POWEROFF_ALARM: { - lcdDrawText(MENUS_MARGIN_LEFT, y, STR_ALARMWARNING); - uint8_t b = 1-g_eeGeneral.disableAlarmWarning; - g_eeGeneral.disableAlarmWarning = 1 - editCheckBox(b, RADIO_SETUP_2ND_COLUMN, y, attr, event); + lcdDrawText(MENUS_MARGIN_LEFT, y, STR_RSSISHUTDOWNALARM); + uint8_t b = 1 - g_eeGeneral.disableRssiPoweroffAlarm; + g_eeGeneral.disableRssiPoweroffAlarm = 1 - editCheckBox(b, RADIO_SETUP_2ND_COLUMN, y, attr, event); break; } @@ -372,18 +376,12 @@ case ITEM_SETUP_BRIGHTNESS: lcdDrawText(MENUS_MARGIN_LEFT, y, STR_BLONBRIGHTNESS); - lcdDrawNumber(RADIO_SETUP_2ND_COLUMN, y, 100-g_eeGeneral.backlightBright, attr|LEFT) ; - if (attr) { - uint8_t b = 100 - g_eeGeneral.backlightBright; - CHECK_INCDEC_GENVAR(event, b, 5, 100); - g_eeGeneral.backlightBright = 100 - b; - } + g_eeGeneral.backlightBright = BACKLIGHT_LEVEL_MAX - editSlider(RADIO_SETUP_2ND_COLUMN, y, event, BACKLIGHT_LEVEL_MAX - g_eeGeneral.backlightBright, BACKLIGHT_LEVEL_MIN, BACKLIGHT_LEVEL_MAX, attr); break; case ITEM_SETUP_DIM_LEVEL: lcdDrawText(MENUS_MARGIN_LEFT, y, STR_BLOFFBRIGHTNESS); - lcdDrawNumber(RADIO_SETUP_2ND_COLUMN, y, g_eeGeneral.blOffBright, attr|LEFT) ; - if (attr) CHECK_INCDEC_GENVAR(event, g_eeGeneral.blOffBright, 5, 100); + g_eeGeneral.blOffBright = editSlider(RADIO_SETUP_2ND_COLUMN, y, event, g_eeGeneral.blOffBright, BACKLIGHT_LEVEL_MIN, BACKLIGHT_LEVEL_MAX, attr); break; case ITEM_SETUP_LABEL_GPS: @@ -428,15 +426,18 @@ g_eeGeneral.imperial = editChoice(RADIO_SETUP_2ND_COLUMN, y, STR_VUNITSSYSTEM, g_eeGeneral.imperial, 0, 1, attr, event); break; -#if 0 +#if defined(FAI_CHOICE) case ITEM_SETUP_FAI: lcdDrawText(MENUS_MARGIN_LEFT, y, PSTR("FAI Mode")); - g_eeGeneral.fai = editCheckBox(g_eeGeneral.fai, RADIO_SETUP_2ND_COLUMN, y, attr, event); - if (attr && checkIncDec_Ret) { - if (g_eeGeneral.fai) - POPUP_WARNING(PSTR("FAI\001mode blocked!")); - else - POPUP_CONFIRMATION(PSTR("FAI mode?")); + if (g_eeGeneral.fai) { + lcdDrawText(RADIO_SETUP_2ND_COLUMN, y, PSTR("Locked in FAI Mode")); + } + else { + g_eeGeneral.fai = editCheckBox(g_eeGeneral.fai, RADIO_SETUP_2ND_COLUMN, y, attr, event); + if (attr && checkIncDec_Ret) { + g_eeGeneral.fai = false; + POPUP_CONFIRMATION(PSTR("FAI mode?")); + } } break; #endif @@ -454,6 +455,11 @@ if (attr) CHECK_INCDEC_GENVAR(event, g_eeGeneral.switchesDelay, -15, 100-15); break; + case ITEM_SETUP_USB_MODE: + lcdDrawText(MENUS_MARGIN_LEFT, y, STR_USBMODE); + g_eeGeneral.USBMode = editChoice(RADIO_SETUP_2ND_COLUMN, y, STR_USBMODES, g_eeGeneral.USBMode, USB_UNSELECTED_MODE, USB_MAX_MODE, attr, event); + break; + case ITEM_SETUP_RX_CHANNEL_ORD: { lcdDrawText(MENUS_MARGIN_LEFT, y, STR_RXCHANNELORD); // RAET->AETR diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/screens_setup.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/screens_setup.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/screens_setup.cpp 2017-05-14 17:18:57.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/screens_setup.cpp 2017-11-20 18:44:06.000000000 +0000 @@ -35,6 +35,7 @@ WidgetsContainerInterface * currentContainer; Widget * currentWidget; uint8_t currentZone; +bool widgetNeedsSettings; #define SCREENS_SETUP_2ND_COLUMN 200 @@ -68,7 +69,7 @@ } } -uint8_t editColorPart(coord_t x, coord_t y, event_t event, uint8_t part, uint8_t value, LcdFlags attr, uint32_t i_flags) +uint8_t editColorPart(coord_t x, coord_t y, event_t event, uint8_t part, uint8_t value, LcdFlags attr, uint32_t i_flags) { const char * STR_COLOR_PARTS = "\002" "R:" "G:" "B:"; uint8_t PART_BITS[] = { 5, 6, 5 }; @@ -76,9 +77,9 @@ lcdDrawNumber(x + 20, y, value << (8-PART_BITS[part]), LEFT|TEXT_COLOR|((attr && (menuHorizontalPosition < 0 || menuHorizontalPosition == part)) ? attr : TEXT_COLOR)); if (attr && menuHorizontalPosition == part) { value = checkIncDec(event, value, 0, (1 << PART_BITS[part])-1, i_flags); - } + } return value; -} +} bool editZoneOption(coord_t y, const ZoneOption * option, ZoneOptionValue * value, LcdFlags attr, uint32_t i_flags, event_t event) { @@ -267,6 +268,7 @@ if (previousWidget) delete previousWidget; currentContainer->createWidget(currentZone, *iterator); + widgetNeedsSettings = currentContainer->getWidget(currentZone)->getFactory()->getOptions(); storageDirty(EE_MODEL); } popMenu(); @@ -377,6 +379,13 @@ } } else { + if (widgetNeedsSettings) { + currentWidget = currentContainer->getWidget(menuVerticalPosition); + if (currentWidget) { + widgetNeedsSettings = false; + onZoneMenu(STR_WIDGET_SETTINGS); + } + } lcdDrawRect(zone.x-padding, zone.y-padding, zone.w+2*padding, zone.h+2*padding, thickness, 0x3F, color); } } @@ -506,7 +515,13 @@ if (index < optionsCount) { const ZoneOption * option = &options[index]; ZoneOptionValue * value = theme->getOptionValue(index); - if (editZoneOption(y, option, value, attr, EE_GENERAL, event)) { + bool ret = editZoneOption(y, option, value, attr, EE_GENERAL, event); + if (option->type == ZoneOption::Color) { + if (attr && event == EVT_KEY_FIRST(KEY_EXIT)) { + theme->update(); + } + } + else if (ret) { theme->update(); } } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/splash.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/splash.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/splash.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/splash.cpp 2017-11-10 17:23:25.000000000 +0000 @@ -29,7 +29,7 @@ #if MENUS_LOCK == 1 if (readonly == false) { - lcdDrawSolidFilledRect((LCD_W-(sizeof(TR_UNLOCKED)-1)*FW)/2 - 9, 50, (sizeof(TR_UNLOCKED)-1)*FW+16, 11, SOLID, ROUND); + lcdDrawSolidFilledRect((LCD_W-(sizeof(TR_UNLOCKED)-1)*FW)/2 - 9, 50, (sizeof(TR_UNLOCKED)-1)*FW+16, 11, SOLID|ROUND); lcdDrawText((LCD_W-(sizeof(TR_UNLOCKED)-1)*FW)/2 , 53, STR_UNLOCKED); } #endif diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/themes/darkblue.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/themes/darkblue.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/themes/darkblue.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/themes/darkblue.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -135,7 +135,16 @@ calibTrackpBackground = BitmapBuffer::load(getThemePath("trackp_background.png")); delete calibHorus; +#if defined(PCBX10) + if(ANALOGS_PWM_ENABLED()) { + calibHorus = BitmapBuffer::load(getThemePath("X10S.bmp")); + } + else { + calibHorus = BitmapBuffer::load(getThemePath("X10.bmp")); + } +#else calibHorus = BitmapBuffer::load(getThemePath("horus.bmp")); +#endif // Channels monitor screen delete chanMonLockedBitmap; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/themes/default.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/themes/default.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/themes/default.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/themes/default.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -46,7 +46,8 @@ lcdColorTable[SCROLLBOX_COLOR_INDEX] = RED; lcdColorTable[MENU_TITLE_BGCOLOR_INDEX] = DARKGREY; lcdColorTable[MENU_TITLE_COLOR_INDEX] = WHITE; - lcdColorTable[MENU_TITLE_DISABLE_COLOR_INDEX] = RGB(130, 1, 5); + lcdColorTable[MENU_TITLE_DISABLE_COLOR_INDEX] = + RGB(GET_RED(RED)>>1, GET_GREEN(RED)>>1, GET_BLUE(RED)>>1); lcdColorTable[HEADER_COLOR_INDEX] = DARKGREY; lcdColorTable[ALARM_COLOR_INDEX] = RED; lcdColorTable[WARNING_COLOR_INDEX] = YELLOW; @@ -173,7 +174,16 @@ calibTrackpBackground = BitmapBuffer::load(getThemePath("trackp_background.png")); delete calibHorus; +#if defined(PCBX10) + if(ANALOGS_PWM_ENABLED()) { + calibHorus = BitmapBuffer::load(getThemePath("X10S.bmp")); + } + else { + calibHorus = BitmapBuffer::load(getThemePath("X10.bmp")); + } +#else calibHorus = BitmapBuffer::load(getThemePath("horus.bmp")); +#endif // Model Selection screen delete modelselIconBitmap; @@ -263,11 +273,16 @@ virtual void update() const { uint32_t color = g_eeGeneral.themeData.options[1].unsignedValue; + uint32_t bg_color = UNEXPECTED_SHUTDOWN() ? WHITE : g_eeGeneral.themeData.options[0].unsignedValue; + + lcdColorTable[TEXT_BGCOLOR_INDEX] = bg_color; lcdColorTable[TEXT_INVERTED_BGCOLOR_INDEX] = color; lcdColorTable[SCROLLBOX_COLOR_INDEX] = color; lcdColorTable[CURVE_COLOR_INDEX] = color; lcdColorTable[CURVE_CURSOR_COLOR_INDEX] = color; lcdColorTable[TITLE_BGCOLOR_INDEX] = color; + lcdColorTable[MENU_TITLE_DISABLE_COLOR_INDEX] = + RGB(GET_RED(color)>>1, GET_GREEN(color)>>1, GET_BLUE(color)>>1); lcdColorTable[TRIM_BGCOLOR_INDEX] = color; lcdColorTable[MAINVIEW_GRAPHICS_COLOR_INDEX] = color; #define DARKER(x) ((x * 70) / 100) diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/view_channels.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/view_channels.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/view_channels.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/view_channels.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -120,7 +120,7 @@ int16_t chanVal = calcRESXto100(channelOutputs[channel]); LimitData * ld = limitAddress(channel); int usValue = PPM_CH_CENTER(channel) + channelOutputs[channel] / 2; - const uint16_t limPos = ld ? posOnBar(calcRESXto100(ld->offset)) : 0; + const uint16_t limPos = ld ? posOnBar(calcRESXto100((ld && ld->revert) ? -ld->offset : ld->offset)) : 0; uint16_t valPos; strAppendSigned(&chanString[2], channel + 1, 2); @@ -132,11 +132,6 @@ lcdDrawSolidFilledRect(x, y + Y_OUTBAR, w, h, BARGRAPH_BGCOLOR); lcd->drawSolidVerticalLine(x + limPos, y + Y_OUTBAR, h, MAINVIEW_GRAPHICS_COLOR); - if (chanVal > 0) - lcdDrawNumber(x - 10 + w / 2, y + h, chanVal, SMLSIZE | TEXT_COLOR | RIGHT, 0, NULL, "%"); - else - lcdDrawNumber(x + 10 + w / 2, y + h, chanVal, SMLSIZE | TEXT_COLOR, 0, NULL, "%"); - chanVal = limit(-VIEW_CHANNELS_LIMIT_PCT, chanVal, VIEW_CHANNELS_LIMIT_PCT); valPos = posOnBar(chanVal); @@ -161,6 +156,10 @@ lcd->drawBitmap(x - X_OFFSET + 7, y + 7, chanMonLockedBitmap); #endif lcd->drawSolidVerticalLine(x + w / 2, y + Y_OUTBAR, h, TEXT_COLOR); + if (chanVal > calcRESXto100((ld && ld->revert) ? -ld->offset : ld->offset)) + lcdDrawNumber(x + limPos, y + h, chanVal, SMLSIZE | TEXT_COLOR | RIGHT, 0, NULL, "%"); + else + lcdDrawNumber(x + limPos, y + h, chanVal, SMLSIZE | TEXT_COLOR, 0, NULL, "%"); } coord_t drawChannelsMonitorLegend(coord_t x, const pm_char * s, int color) diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/view_statistics.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/view_statistics.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/view_statistics.cpp 2017-04-29 16:57:04.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/view_statistics.cpp 2017-11-20 18:44:06.000000000 +0000 @@ -36,7 +36,7 @@ break; } - MENU(STR_STATISTICS, STATS_ICONS, menuTabStats, e_StatsGraph, 0, { 0 }); + SIMPLE_MENU(STR_STATISTICS, STATS_ICONS, menuTabStats, e_StatsGraph, 1); lcdDrawText(MENUS_MARGIN_LEFT, MENU_CONTENT_TOP, "Session"); drawTimer(MENU_STATS_COLUMN1, MENU_CONTENT_TOP, sessionTimer, TIMEHOUR); @@ -89,8 +89,7 @@ prev_yv = yv; } - lcdDrawText(LCD_W/2, MENU_FOOTER_TOP+2, STR_MENUTORESET, CENTERED); - + lcdDrawText(LCD_W/2, MENU_FOOTER_TOP, STR_MENUTORESET, MENU_TITLE_COLOR | CENTERED); return true; } @@ -107,7 +106,7 @@ break; } - MENU("Debug", STATS_ICONS, menuTabStats, e_StatsDebug, 0, { 0 }); + SIMPLE_MENU("Debug", STATS_ICONS, menuTabStats, e_StatsDebug, 1); lcdDrawText(MENUS_MARGIN_LEFT, MENU_CONTENT_TOP, "Free Mem"); lcdDrawNumber(MENU_STATS_COLUMN1, MENU_CONTENT_TOP, availableMemory(), LEFT, 0, NULL, "b"); @@ -148,17 +147,18 @@ lcdDrawText(lcdNextPos+20, MENU_CONTENT_TOP+line*FH+1, "[B]", HEADER_COLOR|SMLSIZE); lcdDrawNumber(lcdNextPos+5, MENU_CONTENT_TOP+line*FH, luaExtraMemoryUsage, LEFT); ++line; - #endif - lcdDrawText(LCD_W/2, MENU_FOOTER_TOP+2, STR_MENUTORESET, CENTERED); + lcdDrawText(MENUS_MARGIN_LEFT, MENU_CONTENT_TOP+line*FH, "Tlm RX Errs"); + lcdDrawNumber(MENU_STATS_COLUMN1, MENU_CONTENT_TOP+line*FH, telemetryErrors, LEFT); + lcdDrawText(LCD_W/2, MENU_FOOTER_TOP, STR_MENUTORESET, MENU_TITLE_COLOR | CENTERED); return true; } bool menuStatsAnalogs(event_t event) { - MENU("Analogs", STATS_ICONS, menuTabStats, e_StatsAnalogs, 0, { 0 }); + SIMPLE_MENU("Analogs", STATS_ICONS, menuTabStats, e_StatsAnalogs, 1); for (uint8_t i=0; ioptions[1].unsignedValue); LcdFlags fontsize = FONTSIZE(persistentData->options[2].unsignedValue << 8); + if(persistentData->options[3].boolValue) { + lcdDrawSizedText(zone.x+1, zone.y+1, persistentData->options[0].stringValue, sizeof(persistentData->options[0].stringValue), ZCHAR|fontsize|BLACK); + } lcdDrawSizedText(zone.x, zone.y, persistentData->options[0].stringValue, sizeof(persistentData->options[0].stringValue), ZCHAR|fontsize|CUSTOM_COLOR); } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/widgets/value.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/widgets/value.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/widgets/value.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/widgets/value.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -36,6 +36,7 @@ const ZoneOption ValueWidget::options[] = { { "Source", ZoneOption::Source, OPTION_VALUE_UNSIGNED(MIXSRC_Rud) }, { "Color", ZoneOption::Color, OPTION_VALUE_UNSIGNED(WHITE) }, + { "Shadow", ZoneOption::Bool, OPTION_VALUE_BOOL(false) }, { NULL, ZoneOption::Bool } }; @@ -45,12 +46,12 @@ mixsrc_t field = persistentData->options[0].unsignedValue; lcdSetColor(persistentData->options[1].unsignedValue); - + int x = zone.x; int y = zone.y; - + // TRACE("w=%d, h=%d", zone.w, zone.h); - + // lcdDrawFilledRect(zone.x, zone.y, zone.w, zone.h, SOLID, MAINVIEW_PANES_COLOR | OPACITY(5)); int xValue, yValue, xLabel, yLabel; @@ -111,11 +112,13 @@ } } - drawSource(xLabel + 1, yLabel + 1, field, attrLabel|BLACK); + if(persistentData->options[2].boolValue) { + drawSource(xLabel + 1, yLabel + 1, field, attrLabel|BLACK); + drawSourceValue(xValue + 1, yValue + 1, field, attrValue|BLACK); + } drawSource(xLabel, yLabel, field, attrLabel|CUSTOM_COLOR); - drawSourceValue(xValue + 1, yValue + 1, field, attrValue|BLACK); drawSourceValue(xValue, yValue, field, attrValue|CUSTOM_COLOR); - + } BaseWidgetFactory ValueWidget("Value", ValueWidget::options); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/widgets.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/widgets.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/widgets.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/widgets.cpp 2017-11-15 20:54:40.000000000 +0000 @@ -314,6 +314,15 @@ return val != 0; } +void drawGVarValue(coord_t x, coord_t y, uint8_t gvar, gvar_t value, LcdFlags flags) +{ + uint8_t prec = g_model.gvars[gvar].prec; + if (prec > 0) { + flags |= (prec == 1 ? PREC1 : PREC2); + } + drawValueWithUnit(x, y, value, g_model.gvars[gvar].unit ? UNIT_PERCENT : UNIT_RAW, flags); +} + int16_t editGVarFieldValue(coord_t x, coord_t y, int16_t value, int16_t min, int16_t max, LcdFlags attr, uint8_t editflags, event_t event) { uint16_t delta = GV_GET_GV1_VALUE(max); @@ -376,7 +385,7 @@ } #define SHUTDOWN_CIRCLE_DIAMETER 150 -void drawShutdownAnimation(uint32_t index) +void drawShutdownAnimation(uint32_t index, const char * message) { static uint32_t last_index = 0xffffffff; static const BitmapBuffer * shutdown = BitmapBuffer::load(getThemePath("shutdown.bmp")); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/widgets.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/widgets.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/480x272/widgets.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/480x272/widgets.h 2017-11-15 20:54:40.000000000 +0000 @@ -59,6 +59,8 @@ void drawSlider(coord_t x, coord_t y, int len, int val, int min, int max, uint8_t steps, uint32_t options); #define drawStatusLine(...) +void drawGVarValue(coord_t x, coord_t y, uint8_t gvar, gvar_t value, LcdFlags flags); + #if defined(GVARS) int16_t editGVarFieldValue(coord_t x, coord_t y, int16_t value, int16_t min, int16_t max, LcdFlags attr, uint8_t editflags, event_t event); #else @@ -69,7 +71,7 @@ void drawMenuTemplate(const char * title, uint8_t icon, const uint8_t * icons=NULL, uint32_t options=0); void drawSplash(); void drawSleepBitmap(); -void drawShutdownAnimation(uint32_t index); +void drawShutdownAnimation(uint32_t index, const char * message); // Main view standard widgets void drawTopBar(); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/common/colorlcd/widgets.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/common/colorlcd/widgets.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/common/colorlcd/widgets.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/common/colorlcd/widgets.cpp 2017-11-15 20:54:40.000000000 +0000 @@ -20,12 +20,14 @@ #include "opentx.h" -void drawStringWithIndex(coord_t x, coord_t y, const char * str, int idx, LcdFlags flags, const char * prefix) +void drawStringWithIndex(coord_t x, coord_t y, const char * str, int idx, LcdFlags flags, const char * prefix, const char * suffix) { char s[64]; char * tmp = (prefix ? strAppend(s, prefix) : s); tmp = strAppend(tmp, str); tmp = strAppendUnsigned(tmp, abs(idx)); + if (suffix) + strAppend(tmp, suffix); lcdDrawText(x, y, s, flags); } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/common/stdlcd/radio_sdmanager.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/common/stdlcd/radio_sdmanager.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/common/stdlcd/radio_sdmanager.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/common/stdlcd/radio_sdmanager.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -174,14 +174,10 @@ #if defined(CPUARM) audioQueue.stopSD(); #endif - BYTE work[_MAX_SS]; - if (f_mkfs(0, FM_FAT32, 0, work, sizeof(work)) == FR_OK) { + if(sdCardFormat()) { f_chdir("/"); REFRESH_FILES(); } - else { - POPUP_WARNING(STR_SDCARD_ERROR); - } } #if LCD_DEPTH > 1 @@ -190,7 +186,7 @@ event_t event = (EVT_KEY_MASK(_event) == KEY_ENTER ? 0 : _event); SIMPLE_MENU(SD_IS_HC() ? STR_SDHC_CARD : STR_SD_CARD, menuTabGeneral, MENU_RADIO_SD_MANAGER, HEADER_LINE + reusableBuffer.sdmanager.count); - + switch (_event) { case EVT_ENTRY: f_chdir(ROOT_PATH); @@ -199,11 +195,11 @@ lastPos = -1; #endif break; - + case EVT_ENTRY_UP: menuVerticalOffset = reusableBuffer.sdmanager.offset; break; - + #if defined(PCBTARANIS) case EVT_KEY_LONG(KEY_MENU): if (!READ_ONLY() && s_editMode == 0) { @@ -340,6 +336,7 @@ res = sdReadDir(&dir, &fno, firstTime); if (res != FR_OK || fno.fname[0] == 0) break; /* Break on error or end of dir */ if (strlen(fno.fname) > SD_SCREEN_FILE_LENGTH) continue; + if (fno.fname[0] == '.' && fno.fname[1] != '.') continue; /* Ignore hidden files under UNIX, but not .. */ reusableBuffer.sdmanager.count++; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/gui_common_arm.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/gui_common_arm.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/gui_common_arm.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/gui_common_arm.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -99,7 +99,7 @@ { if (!isTelemetryFieldAvailable(index)) return false; - + TelemetrySensor & sensor = g_model.telemetrySensors[index]; if (sensor.unit >= UNIT_DATETIME) return false; @@ -354,7 +354,10 @@ } if (swtch >= SWSRC_FIRST_SENSOR && swtch <= SWSRC_LAST_SENSOR) { - return isTelemetryFieldAvailable(swtch - SWSRC_FIRST_SENSOR); + if (context == GeneralCustomFunctionsContext) + return false; + else + return isTelemetryFieldAvailable(swtch - SWSRC_FIRST_SENSOR); } return true; @@ -487,7 +490,7 @@ bool isModuleAvailable(int module) { #if defined(CROSSFIRE) && !defined(PCBFLAMENCO) - if (module == MODULE_TYPE_CROSSFIRE && g_model.moduleData[INTERNAL_MODULE].rfProtocol != RF_PROTO_OFF) { + if (module == MODULE_TYPE_CROSSFIRE && g_model.moduleData[INTERNAL_MODULE].type != MODULE_TYPE_NONE) { return false; } #else @@ -557,14 +560,40 @@ { return true; } -#elif defined(PCBTARANIS) +#elif defined(PCBX9E) +bool isTrainerModeAvailable(int mode) +{ + if (IS_EXTERNAL_MODULE_ENABLED() && (mode == TRAINER_MODE_MASTER_SBUS_EXTERNAL_MODULE || mode == TRAINER_MODE_MASTER_CPPM_EXTERNAL_MODULE)) + return false; +#if defined(USEHORUSBT) + else if (mode == TRAINER_MODE_MASTER_BATTERY_COMPARTMENT) +#else + else if (mode == TRAINER_MODE_MASTER_BLUETOOTH || mode == TRAINER_MODE_MASTER_BATTERY_COMPARTMENT || mode == TRAINER_MODE_SLAVE_BLUETOOTH) +#endif + return false; + else + return true; +} +#elif defined(PCBX9) bool isTrainerModeAvailable(int mode) { - if (IS_EXTERNAL_MODULE_PRESENT() && (mode == TRAINER_MODE_MASTER_SBUS_EXTERNAL_MODULE || mode == TRAINER_MODE_MASTER_CPPM_EXTERNAL_MODULE)) + if (IS_EXTERNAL_MODULE_ENABLED() && (mode == TRAINER_MODE_MASTER_SBUS_EXTERNAL_MODULE || mode == TRAINER_MODE_MASTER_CPPM_EXTERNAL_MODULE)) return false; else return true; } +#elif defined(PCBX7) +bool isTrainerModeAvailable(int mode) +{ + if (mode == TRAINER_MODE_MASTER_SBUS_EXTERNAL_MODULE || mode == TRAINER_MODE_MASTER_CPPM_EXTERNAL_MODULE || mode == TRAINER_MODE_MASTER_BATTERY_COMPARTMENT) + return false; +#if defined(BLUETOOTH) + else if (g_eeGeneral.bluetoothMode != BLUETOOTH_TRAINER && (mode == TRAINER_MODE_MASTER_BLUETOOTH || mode == TRAINER_MODE_SLAVE_BLUETOOTH)) + return false; +#endif + else + return true; +} #endif bool modelHasNotes() @@ -628,7 +657,7 @@ const pm_char STR_SUBTYPE_CX10[] PROGMEM = "\007""Green\0 ""Blue\0 ""DM007\0 ""-\0 ""JC3015a""JC3015b""MK33041""Q242\0 "; -const pm_char STR_SUBTYPE_CG023[] PROGMEM = "\005""CG023""YD829""H8 3d"; +const pm_char STR_SUBTYPE_CG023[] PROGMEM = "\005""CG023""YD829"; const pm_char STR_SUBTYPE_KN[] PROGMEM = "\006""WLtoys""FeiLun"; @@ -646,38 +675,45 @@ const pm_char STR_SUBTYPE_V2X2[] PROGMEM = "\006""V2x2\0 ""JXD506"; -const pm_char STR_SUBTYPE_BAYANG[] PROGMEM = "\006""Bayang""H8S3D"; +const pm_char STR_SUBTYPE_BAYANG[] PROGMEM = "\007""Bayang\0""H8S3D\0 ""X16 AH\0 ""irdrone"; const pm_char STR_SUBTYPE_FY326[] PROGMEM = "\005""FY326""FY319"; +const pm_char STR_SUBTYPE_CABELL[] PROGMEM = "\006""CAB_V3""C_TELM""-\0 ""-\0 ""-\0 ""-\0 ""F_SAFE""UNBIND"; + +const pm_char STR_SUBTYPE_H83D[] PROGMEM = "\006""H8_3D\0""H20H\0 ""H20Mini""H30Mini"; + const mm_protocol_definition multi_protocols[] = { - { MM_RF_PROTO_FLYSKY, STR_SUBTYPE_FLYSKY, 4, nullptr }, - { MM_RF_PROTO_HUBSAN, NO_SUBTYPE, 0, STR_MULTI_VIDFREQ }, - { MM_RF_PROTO_FRSKY, STR_SUBTYPE_FRSKY, 5, STR_MULTI_RFTUNE }, - { MM_RF_PROTO_HISKY, STR_SUBTYPE_HISKY, 1, nullptr }, - { MM_RF_PROTO_V2X2, STR_SUBTYPE_V2X2, 1, nullptr }, - { MM_RF_PROTO_DSM2, STR_SUBTYPE_DSM, 3, nullptr }, - { MM_RF_PROTO_YD717, STR_SUBTYPE_YD717, 4, nullptr }, - { MM_RF_PROTO_KN, STR_SUBTYPE_KN, 1, nullptr }, - { MM_RF_PROTO_SYMAX, STR_SUBTYPE_SYMAX, 1, nullptr }, - { MM_RF_PROTO_SLT, STR_SUBTYPE_SLT, 1, nullptr }, - { MM_RF_PROTO_CX10, STR_SUBTYPE_CX10, 7, nullptr }, - { MM_RF_PROTO_CG023, STR_SUBTYPE_CG023, 2, nullptr }, - { MM_RF_PROTO_BAYANG, STR_SUBTYPE_BAYANG, 1, STR_MULTI_TELEMETRY }, - { MM_RF_PROTO_MT99XX, STR_SUBTYPE_MT99, 4, nullptr }, - { MM_RF_PROTO_MJXQ, STR_SUBTYPE_MJXQ, 5, nullptr }, - { MM_RF_PROTO_FY326, STR_SUBTYPE_FY326, 1, nullptr }, - { MM_RF_PROTO_SFHSS, NO_SUBTYPE, 0, STR_MULTI_RFTUNE }, - { MM_RF_PROTO_HONTAI, STR_SUBTYPE_HONTAI, 2, nullptr }, - { MM_RF_PROTO_OLRS, NO_SUBTYPE, 0, STR_MULTI_RFPOWER }, - { MM_RF_PROTO_FS_AFHDS2A, STR_SUBTYPE_AFHDS2A, 3, STR_MULTI_SERVOFREQ }, - { MM_RF_PROTO_Q2X2, STR_SUBTYPE_Q2X2, 2, nullptr }, - { MM_RF_PROTO_WK_2X01, STR_SUBTYPE_WK2x01, 5, nullptr }, - { MM_RF_PROTO_Q303, STR_SUBTYPE_Q303, 3, nullptr }, - { MM_RF_CUSTOM_SELECTED, NO_SUBTYPE, 7, STR_MULTI_OPTION }, - //Sential and default for protocols not listed above (MM_RF_CUSTOM is 0xff() - { 0xfe, NO_SUBTYPE, 0, nullptr } + {MM_RF_PROTO_FLYSKY, 4, false, STR_SUBTYPE_FLYSKY, nullptr}, + {MM_RF_PROTO_HUBSAN, 0, false, NO_SUBTYPE, STR_MULTI_VIDFREQ}, + {MM_RF_PROTO_FRSKY, 5, false, STR_SUBTYPE_FRSKY, STR_MULTI_RFTUNE}, + {MM_RF_PROTO_HISKY, 1, false, STR_SUBTYPE_HISKY, nullptr}, + {MM_RF_PROTO_V2X2, 1, false, STR_SUBTYPE_V2X2, nullptr}, + {MM_RF_PROTO_DSM2, 3, false, STR_SUBTYPE_DSM, nullptr}, + {MM_RF_PROTO_YD717, 4, false, STR_SUBTYPE_YD717, nullptr}, + {MM_RF_PROTO_KN, 1, false, STR_SUBTYPE_KN, nullptr}, + {MM_RF_PROTO_SYMAX, 1, false, STR_SUBTYPE_SYMAX, nullptr}, + {MM_RF_PROTO_SLT, 1, false, STR_SUBTYPE_SLT, nullptr}, + {MM_RF_PROTO_CX10, 7, false, STR_SUBTYPE_CX10, nullptr}, + {MM_RF_PROTO_CG023, 1, false, STR_SUBTYPE_CG023, nullptr}, + {MM_RF_PROTO_BAYANG, 3, false, STR_SUBTYPE_BAYANG, STR_MULTI_TELEMETRY}, + {MM_RF_PROTO_MT99XX, 4, false, STR_SUBTYPE_MT99, nullptr}, + {MM_RF_PROTO_MJXQ, 5, false, STR_SUBTYPE_MJXQ, nullptr}, + {MM_RF_PROTO_FY326, 1, false, STR_SUBTYPE_FY326, nullptr}, + {MM_RF_PROTO_SFHSS, 0, true, NO_SUBTYPE, STR_MULTI_RFTUNE}, + {MM_RF_PROTO_HONTAI, 2, false, STR_SUBTYPE_HONTAI, nullptr}, + {MM_RF_PROTO_OLRS, 0, false, NO_SUBTYPE, STR_MULTI_RFPOWER}, + {MM_RF_PROTO_FS_AFHDS2A, 3, true, STR_SUBTYPE_AFHDS2A, STR_MULTI_SERVOFREQ}, + {MM_RF_PROTO_Q2X2, 2, false, STR_SUBTYPE_Q2X2, nullptr}, + {MM_RF_PROTO_WK_2X01, 5, false, STR_SUBTYPE_WK2x01, nullptr}, + {MM_RF_PROTO_Q303, 3, false, STR_SUBTYPE_Q303, nullptr}, + {MM_RF_PROTO_CABELL, 7, false, STR_SUBTYPE_CABELL, STR_MULTI_OPTION}, + {MM_RF_PROTO_H83D, 3, false, STR_SUBTYPE_H83D, nullptr}, + {MM_RF_CUSTOM_SELECTED, 7, true, NO_SUBTYPE, STR_MULTI_OPTION}, + + // Sentinel and default for protocols not listed above (MM_RF_CUSTOM is 0xff) + {0xfe, 0, false, NO_SUBTYPE, nullptr} }; #undef NO_SUBTYPE @@ -701,4 +737,4 @@ editName(x, y, g_eeGeneral.anaNames[idx], LEN_ANA_NAME, event, flags); else lcdDrawMMM(x, y, flags); -} \ No newline at end of file +} diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/gui_common.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/gui_common.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/gui/gui_common.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/gui/gui_common.h 2017-12-17 16:22:27.000000000 +0000 @@ -93,6 +93,7 @@ void drawValueWithUnit(coord_t x, coord_t y, int32_t val, uint8_t unit, LcdFlags flags); void drawCurveRef(coord_t x, coord_t y, CurveRef & curve, LcdFlags flags=0); void drawDate(coord_t x, coord_t y, TelemetryItem & telemetryItem, LcdFlags flags=0); +void drawTelemScreenDate(coord_t x, coord_t y, source_t sensor, LcdFlags flags=0); void drawGPSPosition(coord_t x, coord_t y, int32_t longitude, int32_t latitude, LcdFlags flags=0); void drawGPSSensorValue(coord_t x, coord_t y, TelemetryItem & telemetryItem, LcdFlags flags=0); void drawSensorCustomValue(coord_t x, coord_t y, uint8_t sensor, int32_t value, LcdFlags flags=0); @@ -103,7 +104,7 @@ void drawCurve(coord_t offset=0); #if defined(COLORLCD) -void drawStringWithIndex(coord_t x, coord_t y, const char * str, int idx, LcdFlags flags=0, const char * prefix=NULL); +void drawStringWithIndex(coord_t x, coord_t y, const char * str, int idx, LcdFlags flags=0, const char * prefix=NULL, const char * suffix=NULL); int editChoice(coord_t x, coord_t y, const char * values, int value, int min, int max, LcdFlags flags, event_t event); uint8_t editCheckBox(uint8_t value, coord_t x, coord_t y, LcdFlags flags, event_t event); swsrc_t editSwitch(coord_t x, coord_t y, swsrc_t value, LcdFlags flags, event_t event); @@ -114,45 +115,55 @@ void lcdDrawMMM(coord_t x, coord_t y, LcdFlags flags=0); // model_setup Defines that are used in all uis in the same way -#define EXTERNAL_MODULE_CHANNELS_ROWS IF_EXTERNAL_MODULE_ON((IS_MODULE_DSM2(EXTERNAL_MODULE) || IS_MODULE_CROSSFIRE(EXTERNAL_MODULE) || (IS_MODULE_MULTIMODULE(EXTERNAL_MODULE) && g_model.moduleData[EXTERNAL_MODULE].getMultiProtocol(true) != MM_RF_PROTO_DSM2)) ? (uint8_t)0 : (uint8_t)1) +#define EXTERNAL_MODULE_CHANNELS_ROWS IF_EXTERNAL_MODULE_ON((IS_MODULE_DSM2(EXTERNAL_MODULE) || IS_MODULE_CROSSFIRE(EXTERNAL_MODULE) || IS_MODULE_SBUS(EXTERNAL_MODULE) || (IS_MODULE_MULTIMODULE(EXTERNAL_MODULE) && g_model.moduleData[EXTERNAL_MODULE].getMultiProtocol(true) != MM_RF_PROTO_DSM2)) ? (uint8_t)0 : (uint8_t)1) #if defined(MULTIMODULE) -#define MULTIMODULE_STATUS_ROW IS_MODULE_MULTIMODULE(EXTERNAL_MODULE) ? TITLE_ROW : HIDDEN_ROW, -#define MULTIMODULE_MODULE_ROWS IS_MODULE_MULTIMODULE(EXTERNAL_MODULE) ? (uint8_t) 0 : HIDDEN_ROW, IS_MODULE_MULTIMODULE(EXTERNAL_MODULE) ? (uint8_t) 0 : HIDDEN_ROW, +#define MULTIMODULE_STATUS_ROWS IS_MODULE_MULTIMODULE(EXTERNAL_MODULE) ? TITLE_ROW : HIDDEN_ROW, (IS_MODULE_MULTIMODULE(EXTERNAL_MODULE) && multiSyncStatus.isValid()) ? TITLE_ROW : HIDDEN_ROW, +#define MULTIMODULE_MODULE_ROWS IS_MODULE_MULTIMODULE(EXTERNAL_MODULE) ? (uint8_t) 0 : HIDDEN_ROW, #define MULTIMODULE_MODE_ROWS(x) (g_model.moduleData[x].multi.customProto) ? (uint8_t) 3 :MULTIMODULE_HAS_SUBTYPE(g_model.moduleData[x].getMultiProtocol(true)) ? (uint8_t)2 : (uint8_t)1 #define MULTIMODULE_RFPROTO_ROWS(x) (g_model.moduleData[x].multi.customProto) ? (uint8_t) 1 :MULTIMODULE_HAS_SUBTYPE(g_model.moduleData[x].getMultiProtocol(true)) ? (uint8_t) 0 : HIDDEN_ROW #define MULTIMODULE_SUBTYPE_ROWS(x) IS_MODULE_MULTIMODULE(x) ? MULTIMODULE_RFPROTO_ROWS(x) : HIDDEN_ROW, #define MULTIMODULE_HAS_SUBTYPE(x) (getMultiProtocolDefinition(x)->maxSubtype > 0) #define MULTIMODULE_HASOPTIONS(x) (getMultiProtocolDefinition(x)->optionsstr != nullptr) -#define MULTIMODULE_FAILSAFEROWS(x) (IS_MODULE_MULTIMODULE(x) && (MULTIMODULE_HASOPTIONS(g_model.moduleData[x].getMultiProtocol(true)))) ? (uint8_t) 0: HIDDEN_ROW #define MULTI_MAX_RX_NUM(x) (g_model.moduleData[x].getMultiProtocol(true) == MM_RF_PROTO_OLRS ? 4 : 15) -// only packed to save flash -PACK( - struct mm_protocol_definition { - uint8_t protocol; - const pm_char *subTypeString; - uint8_t maxSubtype; - const char *optionsstr; - } ); +#define MULTIMODULE_HASFAILSAFE(x) (IS_MODULE_MULTIMODULE(x) && multiModuleStatus.isValid() && multiModuleStatus.supportsFailsafe()) +#define MULTIMODULE_OPTIONS_ROW (IS_MODULE_MULTIMODULE(EXTERNAL_MODULE) && MULTIMODULE_HASOPTIONS(g_model.moduleData[EXTERNAL_MODULE].getMultiProtocol(true))) ? (uint8_t) 0: HIDDEN_ROW + +// When using packed, the pointer in here end up not being aligned, which clang and gcc complain about +// Keep the order of the fields that the so that the size stays small +struct mm_protocol_definition { + uint8_t protocol; + uint8_t maxSubtype; + bool failsafe; + const pm_char *subTypeString; + const char *optionsstr; +}; const mm_protocol_definition *getMultiProtocolDefinition (uint8_t protocol); #else -#define MULTIMODULE_STATUS_ROW +#define MULTIMODULE_STATUS_ROWS #define MULTIMODULE_MODULE_ROWS -#define MULTIMODULE_FAILSAFEROWS(x) HIDDEN_ROW +#define MULTIMODULE_HASFAILSAFE(x) false #define MULTIMODULE_SUBTYPE_ROWS(x) #define MULTIMODULE_MODE_ROWS(x) (uint8_t)0 #define MULTI_MAX_RX_NUM(x) 15 +#define MULTIMODULE_OPTIONS_ROW HIDDEN_ROW #endif -#define MAX_RX_NUM(x) (IS_MODULE_DSM2(x) ? 20 : IS_MODULE_MULTIMODULE(x) ? MULTI_MAX_RX_NUM(x) : 63) +#define MAX_RX_NUM(x) (IS_MODULE_DSM2(x) ? 20 : IS_MODULE_MULTIMODULE(x) ? MULTI_MAX_RX_NUM(x) : 63) #define IS_D8_RX(x) (g_model.moduleData[x].rfProtocol == RF_PROTO_D8) -#define IF_TRAINER_ON(x) (g_model.trainerMode == TRAINER_MODE_SLAVE ? (uint8_t)(x) : HIDDEN_ROW) +#define IS_R9M_OR_XJTD16(x) ((IS_MODULE_XJT(x) && g_model.moduleData[x].rfProtocol== RF_PROTO_X16) || IS_MODULE_R9M(x)) -#define FAILSAFE_ROWS(x) (IS_MODULE_XJT(x) && HAS_RF_PROTOCOL_FAILSAFE(g_model.moduleData[x].rfProtocol) ? (g_model.moduleData[x].failsafeMode==FAILSAFE_CUSTOM ? (uint8_t)1 : (uint8_t)0) : MULTIMODULE_FAILSAFEROWS(x)) +#define FAILSAFE_ROWS(x) ((IS_MODULE_XJT(x) && HAS_RF_PROTOCOL_FAILSAFE(g_model.moduleData[x].rfProtocol)) || MULTIMODULE_HASFAILSAFE(x) || IS_MODULE_R9M(x)) ? (g_model.moduleData[x].failsafeMode==FAILSAFE_CUSTOM ? (uint8_t)1 : (uint8_t)0) : HIDDEN_ROW +#define R9M_FCC_OPTION_ROW (IS_TELEMETRY_INTERNAL_MODULE() ? TITLE_ROW : (uint8_t)0) +#define R9M_OPTION_ROW (IS_MODULE_R9M_FCC(EXTERNAL_MODULE) ? R9M_FCC_OPTION_ROW : TITLE_ROW) +#define EXTERNAL_MODULE_OPTION_ROW (IS_MODULE_R9M(EXTERNAL_MODULE) ? R9M_OPTION_ROW : (IS_MODULE_SBUS(EXTERNAL_MODULE) ? TITLE_ROW : MULTIMODULE_OPTIONS_ROW)) +#define EXTERNAL_MODULE_POWER_ROW (IS_MODULE_MULTIMODULE(EXTERNAL_MODULE) || IS_MODULE_R9M_FCC(EXTERNAL_MODULE)) ? (uint8_t) 0 : HIDDEN_ROW void editStickHardwareSettings(coord_t x, coord_t y, int idx, event_t event, LcdFlags flags); + + #endif // _GUI_COMMON_H_ diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/keys.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/keys.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/keys.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/keys.h 2017-10-31 16:16:43.000000000 +0000 @@ -2,7 +2,7 @@ * Copyright (C) OpenTX * * Based on code named - * th9x - http://code.google.com/p/th9x + * th9x - http://code.google.com/p/th9x * er9x - http://code.google.com/p/er9x * gruvin9x - http://code.google.com/p/gruvin9x * diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/lua/api_general.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/lua/api_general.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/lua/api_general.cpp 2017-05-31 19:49:19.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/lua/api_general.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -56,13 +56,13 @@ @retval multiple (available since 2.1.7) returns 5 values: * (string) OpenTX version (ie "2.1.5") - * (string) radio version: `x9e`, `x9d+` or `x9d`. + * (string) radio type: `x12s`, `x10`, `x9e`, `x9d+`, `x9d` or `x7`. If running in simulator the "-simu" is added * (number) major version (ie 2 if version 2.1.5) * (number) minor version (ie 1 if version 2.1.5) * (number) revision number (ie 5 if version 2.1.5) -@status current Introduced in 2.0.0, expanded in 2.1.7 +@status current Introduced in 2.0.0, expanded in 2.1.7, radio type strings changed in 2.2.0 ### Example @@ -108,7 +108,7 @@ @retval number Number of 10ms ticks since the radio was started Example: run time: 12.54 seconds, return value: 1254 -The timer internally uses a 32-bit counter which is enough for 30year so +The timer internally uses a 32-bit counter which is enough for 30 years so overflows will not happen. @status current Introduced in 2.0.0 @@ -122,13 +122,28 @@ static void luaPushDateTime(lua_State * L, uint32_t year, uint32_t mon, uint32_t day, uint32_t hour, uint32_t min, uint32_t sec) { - lua_createtable(L, 0, 6); + uint32_t hour12 = hour; + + if (hour == 0) { + hour12 = 12; + } + else if (hour > 12) { + hour12 = hour - 12; + } + lua_createtable(L, 0, 8); lua_pushtableinteger(L, "year", year); lua_pushtableinteger(L, "mon", mon); lua_pushtableinteger(L, "day", day); lua_pushtableinteger(L, "hour", hour); lua_pushtableinteger(L, "min", min); lua_pushtableinteger(L, "sec", sec); + lua_pushtableinteger(L, "hour12", hour12); + if (hour < 12) { + lua_pushtablestring(L, "suffix", "am"); + } + else { + lua_pushtablestring(L, "suffix", "pm"); + } } /*luadoc @@ -141,8 +156,10 @@ * `mon` (number) month * `day` (number) day of month * `hour` (number) hours + * `hour12` (number) hours in US format * `min` (number) minutes * `sec` (number) seconds + * `suffix` (text) am or pm */ static int luaGetDateTime(lua_State * L) { @@ -311,7 +328,9 @@ (frame ID == 0x10), as well as packets with a frame ID equal 0x32 (regardless of the data ID) will be passed to the LUA telemetry receive queue. -@retval SPORT paket as a quadruple: +@retval nil queue does not contain any (or enough) bytes to form a whole packet + +@retval multiple returns 4 values: * sensor ID (number) * frame ID (number) * data ID (number) @@ -359,7 +378,7 @@ This functions allows for sending SPORT telemetry data toward the receiver, and more generally, to anything connected SPORT bus on the receiver or transmitter. -When called without parameters, it will only return the status of the ouput buffer without sending anything. +When called without parameters, it will only return the status of the output buffer without sending anything. @param sensorId physical sensor ID @@ -396,11 +415,13 @@ /*luadoc @function crossfireTelemetryPop() -@retval SPORT paket as a quadruple: - * sensor ID (number) - * frame ID (number) - * data ID (number) - * value (number) +Pops a received Crossfire Telemetry packet from the queue. + +@retval nil queue does not contain any (or enough) bytes to form a whole packet + +@retval multiple returns 2 values: + * command (number) + * packet (table) data bytes @status current Introduced in 2.2.0 */ @@ -437,15 +458,11 @@ This functions allows for sending telemetry data toward the TBS Crossfire link. -When called without parameters, it will only return the status of the ouput buffer without sending anything. +When called without parameters, it will only return the status of the output buffer without sending anything. -@param sensorId physical sensor ID +@param command command -@param frameId frame ID - -@param dataId data ID - -@param value value +@param data table of data bytes @retval boolean data queued in output buffer or not. @@ -773,6 +790,8 @@ int pause = luaL_checkinteger(L, 2); int flags = luaL_optinteger(L, 3, 0); haptic.play(length, pause, flags); +#else + UNUSED(L); #endif return 0; } @@ -824,6 +843,7 @@ Returns (some of) the general radio settings @retval table with elements: + * `battWarn` (number) radio battery range - warning value * `battMin` (number) radio battery range - minimum value * `battMax` (number) radio battery range - maximum value * `imperial` (number) set to a value different from 0 if the radio is set to the @@ -838,6 +858,7 @@ static int luaGetGeneralSettings(lua_State * L) { lua_newtable(L); + lua_pushtablenumber(L, "battWarn", (g_eeGeneral.vBatWarn) * 0.1f); lua_pushtablenumber(L, "battMin", (90+g_eeGeneral.vBatMin) * 0.1f); lua_pushtablenumber(L, "battMax", (120+g_eeGeneral.vBatMax) * 0.1f); lua_pushtableinteger(L, "imperial", g_eeGeneral.imperial); @@ -1085,8 +1106,8 @@ static int luaGetRSSI(lua_State * L) { lua_pushunsigned(L, min((uint8_t)99, TELEMETRY_RSSI())); - lua_pushunsigned(L, getRssiAlarmValue(0)); - lua_pushunsigned(L, getRssiAlarmValue(1)); + lua_pushunsigned(L, g_model.rssiAlarms.getWarningRssi()); + lua_pushunsigned(L, g_model.rssiAlarms.getCriticalRssi()); return 3; } @@ -1169,6 +1190,21 @@ } } +/*luadoc +@function getUsage() + +Get percent of already used Lua instructions in current script execution cycle. + +@retval usage (number) a value from 0 to 100 (percent) + +@status current Introduced in 2.2.1 +*/ +static int luaGetUsage(lua_State * L) +{ + lua_pushinteger(L, instructionsPercent); + return 1; +} + const luaL_Reg opentxLib[] = { { "getTime", luaGetTime }, { "getDateTime", luaGetDateTime }, @@ -1191,6 +1227,7 @@ { "getRSSI", luaGetRSSI }, { "killEvents", luaKillEvents }, { "loadScript", luaLoadScript }, + { "getUsage", luaGetUsage }, #if LCD_DEPTH > 1 && !defined(COLORLCD) { "GREY", luaGrey }, #endif @@ -1238,7 +1275,9 @@ { "MIXSRC_CH1", MIXSRC_CH1 }, { "SWSRC_LAST", SWSRC_LAST_LOGICAL_SWITCH }, #if defined(COLORLCD) + { "SHADOWED", SHADOWED }, { "COLOR", ZoneOption::Color }, + { "BOOL", ZoneOption::Bool }, { "CUSTOM_COLOR", CUSTOM_COLOR }, { "TEXT_COLOR", TEXT_COLOR }, { "TEXT_BGCOLOR", TEXT_BGCOLOR }, diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/lua/api_lcd.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/lua/api_lcd.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/lua/api_lcd.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/lua/api_lcd.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -205,8 +205,9 @@ * `SMLSIZE` small font * `INVERS` inverted display * `BLINK` blinking text + * `SHADOWED` Horus only, apply a shadow effect -@status current Introduced in 2.0.0 +@status current Introduced in 2.0.0, `SHADOWED` introduced in 2.2.1 */ static int luaLcdDrawText(lua_State *L) { @@ -215,6 +216,9 @@ int y = luaL_checkinteger(L, 2); const char * s = luaL_checkstring(L, 3); unsigned int att = luaL_optunsigned(L, 4, 0); + #if defined(COLORLCD) + if ((att&SHADOWED) && !(att&INVERS)) lcdDrawText(x+1, y+1, s, att&0xFFFF); + #endif lcdDrawText(x, y, s, att); return 0; } @@ -232,8 +236,9 @@ * `0 or not specified` normal representation (minutes and seconds) * `TIMEHOUR` display hours * other general LCD flag also apply + * `SHADOWED` Horus only, apply a shadow effect -@status current Introduced in 2.0.0 +@status current Introduced in 2.0.0, `SHADOWED` introduced in 2.2.1 */ static int luaLcdDrawTimer(lua_State *L) { @@ -243,6 +248,7 @@ int seconds = luaL_checkinteger(L, 3); unsigned int att = luaL_optunsigned(L, 4, 0); #if defined(COLORLCD) + if (att&SHADOWED) drawTimer(x+1, y+1, seconds, (att&0xFFFF)|LEFT); drawTimer(x, y, seconds, att|LEFT); #else drawTimer(x, y, seconds, att|LEFT, att); @@ -264,8 +270,9 @@ * `PREC1` display with one decimal place (number 386 is displayed as 38.6) * `PREC2` display with tow decimal places (number 386 is displayed as 3.86) * other general LCD flag also apply + * `SHADOWED` Horus only, apply a shadow effect -@status current Introduced in 2.0.0 +@status current Introduced in 2.0.0, `SHADOWED` introduced in 2.2.1 */ static int luaLcdDrawNumber(lua_State *L) { @@ -274,6 +281,9 @@ int y = luaL_checkinteger(L, 2); int val = luaL_checkinteger(L, 3); unsigned int att = luaL_optunsigned(L, 4, 0); + #if defined(COLORLCD) + if ((att&SHADOWED) && !(att&INVERS)) lcdDrawNumber(x, y, val, att&0xFFFF); + #endif lcdDrawNumber(x, y, val, att); return 0; } @@ -521,7 +531,7 @@ } return 0; } -#elif LCD_DEPTH > 1 +#else /*luadoc @function lcd.drawPixmap(x, y, name) @@ -701,8 +711,6 @@ @param idx (integer) index of entry to highlight -@param page (number) page number - @param flags (unsigned number) drawing flags, the flags can not be combined: * `BLINK` combo box is expanded * `INVERS` combo box collapsed, text inversed @@ -865,19 +873,13 @@ { "drawBitmap", luaLcdDrawBitmap }, { "setColor", luaLcdSetColor }, { "RGB", luaRGB }, -#elif LCD_DEPTH > 1 +#else { "getLastPos", luaLcdGetLastPos }, { "getLastRightPos", luaLcdGetLastPos }, { "getLastLeftPos", luaLcdGetLeftPos }, { "drawPixmap", luaLcdDrawPixmap }, { "drawScreenTitle", luaLcdDrawScreenTitle }, { "drawCombobox", luaLcdDrawCombobox }, -#else - { "drawScreenTitle", luaLcdDrawScreenTitle }, - { "getLastPos", luaLcdGetLastPos }, - { "getLastRightPos", luaLcdGetLastPos }, - { "getLastLeftPos", luaLcdGetLeftPos }, - { "drawCombobox", luaLcdDrawCombobox }, #endif { NULL, NULL } /* sentinel */ }; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/lua/api_model.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/lua/api_model.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/lua/api_model.cpp 2017-05-31 19:49:19.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/lua/api_model.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -833,7 +833,7 @@ lua_pushstring(L, "x"); lua_newtable(L); lua_pushinteger(L, 0); - lua_pushinteger(L, 0); + lua_pushinteger(L, -100); lua_settable(L, -3); for (int i=0; i < curveData.points + 3; i++) { lua_pushinteger(L, i+1); @@ -961,7 +961,7 @@ if (newCurveData.type == CURVE_TYPE_CUSTOM) { - // The rest of the points are checked by the monotic condition + // The rest of the points are checked by the monotonic condition for (unsigned int i=numPoints; i < sizeof(xPoints);i++) { if (xPoints[i] != -127) @@ -1031,7 +1031,7 @@ if (destCurveData.type == CURVE_TYPE_CUSTOM) { for (int i = 1; i < destCurveData.points + 4; i++) { - *point++ = yPoints[i]; + *point++ = xPoints[i]; } } storageDirty(EE_MODEL); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/lua/interface.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/lua/interface.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/lua/interface.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/lua/interface.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -44,13 +44,46 @@ uint16_t maxLuaInterval = 0; uint16_t maxLuaDuration = 0; bool luaLcdAllowed; -int instructionsPercent = 0; +uint8_t instructionsPercent = 0; char lua_warning_info[LUA_WARNING_INFO_LEN+1]; struct our_longjmp * global_lj = 0; #if defined(COLORLCD) uint32_t luaExtraMemoryUsage = 0; #endif +#if defined(LUA_ALLOCATOR_TRACER) + +LuaMemTracer lsScriptsTrace; + +#if defined(PCBHORUS) + extern LuaMemTracer lsWidgetsTrace; + #define GET_TRACER(L) (L == lsScripts) ? &lsScriptsTrace : &lsWidgetsTrace +#else + #define GET_TRACER(L) &lsScriptsTrace +#endif + +void *tracer_alloc(void * ud, void * ptr, size_t osize, size_t nsize) +{ + LuaMemTracer * tracer = (LuaMemTracer *)ud; + if (ptr) { + if (osize < nsize) { + // TRACE("Lua alloc %u", nsize - osize); + tracer->alloc += nsize - osize; + } + else { + // TRACE("Lua free %u", osize - nsize); + tracer->free += osize - nsize; + } + } + else { + // TRACE("Lua alloc %u (type %s)", nsize, osize < LUA_TOTALTAGS ? lua_typename(0, osize) : "unk"); + tracer->alloc += nsize; + } + return l_alloc(ud, ptr, osize, nsize); +} + +#endif // #if defined(LUA_ALLOCATOR_TRACER) + /* custom panic handler */ int custom_lua_atpanic(lua_State * L) { @@ -64,19 +97,53 @@ void luaHook(lua_State * L, lua_Debug *ar) { - instructionsPercent++; + if (ar->event == LUA_HOOKCOUNT) { + instructionsPercent++; +#if defined(DEBUG) + // Disable Lua script instructions limit in DEBUG mode, + // just report max value reached + static uint16_t max = 0; if (instructionsPercent > 100) { - // From now on, as soon as a line is executed, error - // keep erroring until you're script reaches the top - lua_sethook(L, luaHook, LUA_MASKLINE, 0); - luaL_error(L, "CPU limit"); + if (max + 10 < instructionsPercent) { + max = instructionsPercent; + TRACE("LUA instructionsPercent %u%%", (uint32_t)max); + } + } + else if (instructionsPercent < 10) { + max = 0; + } +#else + if (instructionsPercent > 100) { + // From now on, as soon as a line is executed, error + // keep erroring until you're script reaches the top + lua_sethook(L, luaHook, LUA_MASKLINE, 0); + luaL_error(L, "CPU limit"); + } +#endif + } +#if defined(LUA_ALLOCATOR_TRACER) + else if (ar->event == LUA_HOOKLINE) { + lua_getinfo(L, "nSl", ar); + LuaMemTracer * tracer = GET_TRACER(L); + if (tracer->alloc || tracer->free) { + TRACE("LT: [+%u,-%u] %s:%d", tracer->alloc, tracer->free, tracer->script, tracer->lineno); + } + tracer->script = ar->source; + tracer->lineno = ar->currentline; + tracer->alloc = 0; + tracer->free = 0; } +#endif // #if defined(LUA_ALLOCATOR_TRACER) } void luaSetInstructionsLimit(lua_State * L, int count) { - instructionsPercent=0; + instructionsPercent = 0; +#if defined(LUA_ALLOCATOR_TRACER) + lua_sethook(L, luaHook, LUA_MASKCOUNT|LUA_MASKLINE, count); +#else lua_sethook(L, luaHook, LUA_MASKCOUNT, count); +#endif } int luaGetInputs(lua_State * L, ScriptInputsOutputs & sid) @@ -174,6 +241,14 @@ PROTECT_LUA() { TRACE("luaClose %p", *L); lua_close(*L); // this should not panic, but we make sure anyway +#if defined(LUA_ALLOCATOR_TRACER) + LuaMemTracer * tracer = GET_TRACER(*L); + if (tracer->alloc || tracer->free) { + TRACE("LT: [+%u,-%u] luaClose(%s)", tracer->alloc, tracer->free, (*L == lsScripts) ? "scipts" : "widgets"); + } + tracer->alloc = 0; + tracer->free = 0; +#endif // #if defined(LUA_ALLOCATOR_TRACER) } else { // we can only disable Lua for the rest of the session @@ -556,14 +631,14 @@ return true; } -bool luaLoadFunctionScript(uint8_t index) +bool luaLoadFunctionScript(uint8_t index, uint8_t ref) { - CustomFunctionData & fn = g_model.customFn[index]; + CustomFunctionData & fn = (ref < SCRIPT_GFUNC_FIRST ? g_model.customFn[index] : g_eeGeneral.customFn[index]); if (fn.func == FUNC_PLAY_SCRIPT && ZEXIST(fn.play.name)) { if (luaScriptsCount < MAX_SCRIPTS) { ScriptInternalData & sid = scriptInternalData[luaScriptsCount++]; - sid.reference = SCRIPT_FUNC_FIRST+index; + sid.reference = ref + index; sid.state = SCRIPT_NOFILE; char filename[sizeof(SCRIPTS_FUNCS_PATH)+sizeof(fn.play.name)+sizeof(SCRIPT_EXT)] = SCRIPTS_FUNCS_PATH "/"; strncpy(filename+sizeof(SCRIPTS_FUNCS_PATH), fn.play.name, sizeof(fn.play.name)); @@ -637,7 +712,7 @@ // Load custom function scripts for (int i=0; iinputs[j].def); } } - else if ((scriptType & RUN_FUNC_SCRIPT) && (sid.reference >= SCRIPT_FUNC_FIRST && sid.reference <= SCRIPT_FUNC_LAST)) { - CustomFunctionData & fn = g_model.customFn[sid.reference-SCRIPT_FUNC_FIRST]; + else if ((scriptType & RUN_FUNC_SCRIPT) && (sid.reference >= SCRIPT_FUNC_FIRST && sid.reference <= SCRIPT_GFUNC_LAST)) { + CustomFunctionData & fn = (sid.reference < SCRIPT_GFUNC_FIRST ? g_model.customFn[sid.reference-SCRIPT_FUNC_FIRST] : g_eeGeneral.customFn[sid.reference-SCRIPT_GFUNC_FIRST]); #if defined(SIMU) || defined(DEBUG) filename = fn.play.name; #endif @@ -1002,6 +1077,10 @@ if (luaState != INTERPRETER_PANIC) { #if defined(USE_BIN_ALLOCATOR) lsScripts = lua_newstate(bin_l_alloc, NULL); //we use our own allocator! +#elif defined(LUA_ALLOCATOR_TRACER) + memset(&lsScriptsTrace, 0 , sizeof(lsScriptsTrace)); + lsScriptsTrace.script = "lua_newstate(scripts)"; + lsScripts = lua_newstate(tracer_alloc, &lsScriptsTrace); //we use tracer allocator #else lsScripts = lua_newstate(l_alloc, NULL); //we use Lua default allocator #endif @@ -1009,6 +1088,10 @@ // install our panic handler lua_atpanic(lsScripts, &custom_lua_atpanic); +#if defined(LUA_ALLOCATOR_TRACER) + lua_sethook(lsScripts, luaHook, LUA_MASKLINE, 0); +#endif + // protect libs and constants registration PROTECT_LUA() { luaRegisterLibraries(lsScripts); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/lua/lua_api.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/lua/lua_api.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/lua/lua_api.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/lua/lua_api.h 2017-12-17 16:22:27.000000000 +0000 @@ -98,7 +98,9 @@ SCRIPT_MIX_FIRST, SCRIPT_MIX_LAST=SCRIPT_MIX_FIRST+MAX_SCRIPTS-1, SCRIPT_FUNC_FIRST, - SCRIPT_FUNC_LAST=SCRIPT_FUNC_FIRST+MAX_SPECIAL_FUNCTIONS-1, + SCRIPT_FUNC_LAST=SCRIPT_FUNC_FIRST+MAX_SPECIAL_FUNCTIONS-1, // model functions + SCRIPT_GFUNC_FIRST, + SCRIPT_GFUNC_LAST=SCRIPT_GFUNC_FIRST+MAX_SPECIAL_FUNCTIONS-1, // global functions SCRIPT_TELEMETRY_FIRST, SCRIPT_TELEMETRY_LAST=SCRIPT_TELEMETRY_FIRST+MAX_SCRIPTS, // telem0 and telem1 .. telem7 }; @@ -151,6 +153,7 @@ extern uint16_t maxLuaInterval; extern uint16_t maxLuaDuration; +extern uint8_t instructionsPercent; #if defined(PCBTARANIS) #define IS_MASKABLE(key) ((key) != KEY_EXIT && (key) != KEY_ENTER && ((luaState & INTERPRETER_RUNNING_STANDALONE_SCRIPT) || (key) != KEY_PAGE)) @@ -167,10 +170,24 @@ void registerBitmapClass(lua_State * L); void luaSetInstructionsLimit(lua_State* L, int count); int luaLoadScriptFileToState(lua_State * L, const char * filename, const char * mode); + +struct LuaMemTracer { + const char * script; + int lineno; + uint32_t alloc; + uint32_t free; +}; + +void * tracer_alloc(void * ud, void * ptr, size_t osize, size_t nsize); +void luaHook(lua_State * L, lua_Debug *ar); + + #else // defined(LUA) + #define luaInit() #define LUA_INIT_THEMES_AND_WIDGETS() #define LUA_LOAD_MODEL_SCRIPTS() + #endif // defined(LUA) #endif // _LUA_API_H_ diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/lua/widgets.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/lua/widgets.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/lua/widgets.cpp 2017-05-14 17:18:57.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/lua/widgets.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -113,7 +113,6 @@ } else if (option->type == ZoneOption::Source || option->type == ZoneOption::TextSize || - option->type == ZoneOption::Source || option->type == ZoneOption::Color) { luaL_checktype(lsWidgets, -1, LUA_TNUMBER); // value is number option->deflt.unsignedValue = lua_tounsigned(lsWidgets, -1); @@ -234,14 +233,17 @@ } if (name) { - ZoneOption * options = createOptionsArray(themeOptions, MAX_THEME_OPTIONS); - if (options) { - LuaTheme * theme = new LuaTheme(name, options); - theme->loadFunction = loadFunction; - theme->drawBackgroundFunction = drawBackgroundFunction; - theme->drawTopbarBackgroundFunction = drawTopbarBackgroundFunction; - TRACE("Loaded Lua theme %s", name); - } + ZoneOption * options = NULL; + if (themeOptions) { + options = createOptionsArray(themeOptions, MAX_THEME_OPTIONS); + if (!options) + return; + } + LuaTheme * theme = new LuaTheme(name, options); + theme->loadFunction = loadFunction; + theme->drawBackgroundFunction = drawBackgroundFunction; + theme->drawTopbarBackgroundFunction = drawTopbarBackgroundFunction; // NOSONAR + TRACE("Loaded Lua theme %s", name); } } @@ -446,7 +448,7 @@ LuaWidgetFactory * factory = new LuaWidgetFactory(name, options, createFunction); factory->updateFunction = updateFunction; factory->refreshFunction = refreshFunction; - factory->backgroundFunction = backgroundFunction; + factory->backgroundFunction = backgroundFunction; // NOSONAR TRACE("Loaded Lua widget %s", name); } } @@ -514,12 +516,20 @@ f_closedir(&dir); } +#if defined(LUA_ALLOCATOR_TRACER) +LuaMemTracer lsWidgetsTrace; +#endif + void luaInitThemesAndWidgets() { TRACE("luaInitThemesAndWidgets"); #if defined(USE_BIN_ALLOCATOR) lsWidgets = lua_newstate(bin_l_alloc, NULL); //we use our own allocator! +#elif defined(LUA_ALLOCATOR_TRACER) + memset(&lsWidgetsTrace, 0 , sizeof(lsWidgetsTrace)); + lsWidgetsTrace.script = "lua_newstate(widgets)"; + lsWidgets = lua_newstate(tracer_alloc, &lsWidgetsTrace); //we use tracer allocator #else lsWidgets = lua_newstate(l_alloc, NULL); //we use Lua default allocator #endif @@ -527,6 +537,10 @@ // install our panic handler lua_atpanic(lsWidgets, &custom_lua_atpanic); +#if defined(LUA_ALLOCATOR_TRACER) + lua_sethook(lsWidgets, luaHook, LUA_MASKLINE, 0); +#endif + // protect libs and constants registration PROTECT_LUA() { luaRegisterLibraries(lsWidgets); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/main_arm.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/main_arm.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/main_arm.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/main_arm.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -24,20 +24,51 @@ uint8_t requiredSpeakerVolume = 255; uint8_t mainRequestFlags = 0; +#if defined(STM32) +void onUSBConnectMenu(const char *result) +{ + if (result == STR_USB_MASS_STORAGE) { + setSelectedUsbMode(USB_MASS_STORAGE_MODE); + } + else if (result == STR_USB_JOYSTICK) { + setSelectedUsbMode(USB_JOYSTICK_MODE); + } + else if (result == STR_USB_SERIAL) { + setSelectedUsbMode(USB_SERIAL_MODE); + } +} +#endif + void handleUsbConnection() { #if defined(STM32) && !defined(SIMU) - if (!usbStarted() && usbPlugged()) { + if (!usbStarted() && usbPlugged() && !(getSelectedUsbMode() == USB_UNSELECTED_MODE)) { usbStart(); -#if defined(USB_MASS_STORAGE) - opentxClose(false); - usbPluggedIn(); + if (getSelectedUsbMode() == USB_MASS_STORAGE_MODE) { + opentxClose(false); + usbPluggedIn(); + } + } + if (!usbStarted() && usbPlugged() && getSelectedUsbMode() == USB_UNSELECTED_MODE) { + if((g_eeGeneral.USBMode == USB_UNSELECTED_MODE) && (popupMenuNoItems == 0)) { + POPUP_MENU_ADD_ITEM(STR_USB_JOYSTICK); + POPUP_MENU_ADD_ITEM(STR_USB_MASS_STORAGE); +#if defined(DEBUG) + POPUP_MENU_ADD_ITEM(STR_USB_SERIAL); #endif + POPUP_MENU_START(onUSBConnectMenu); + } + if (g_eeGeneral.USBMode != USB_UNSELECTED_MODE) { + setSelectedUsbMode(g_eeGeneral.USBMode); + } } if (usbStarted() && !usbPlugged()) { usbStop(); -#if defined(USB_MASS_STORAGE) && !defined(EEPROM) - opentxResume(); + if (getSelectedUsbMode() == USB_MASS_STORAGE_MODE) { + opentxResume(); + } +#if !defined(BOOT) + setSelectedUsbMode(USB_UNSELECTED_MODE); #endif } #endif // defined(STM32) && !defined(SIMU) @@ -402,12 +433,10 @@ return; } #endif - -#if defined(PCBHORUS) - // TODO if it is OK on HORUS it could be ported to all other boards - // But in this case it's needed to define sdMount for all boards, because sdInit also initializes the SD mutex - static uint32_t sdcard_present_before = SD_CARD_PRESENT(); - uint32_t sdcard_present_now = SD_CARD_PRESENT(); + +#if defined(STM32) + static bool sdcard_present_before = SD_CARD_PRESENT(); + bool sdcard_present_now = SD_CARD_PRESENT(); if (sdcard_present_now && !sdcard_present_before) { sdMount(); } @@ -421,9 +450,9 @@ return; } #endif - -#if defined(USB_MASS_STORAGE) - if (usbPlugged()) { + +#if defined(STM32) + if (usbPlugged() && getSelectedUsbMode() == USB_MASS_STORAGE_MODE) { // disable access to menus lcdClear(); menuMainView(0); @@ -455,12 +484,7 @@ toplcdRefreshEnd(); #endif -#if defined(BLUETOOTH) && !defined(SIMU) - bluetoothWakeup(); -#endif - #if defined(INTERNAL_GPS) gpsWakeup(); #endif } - diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/myeeprom.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/myeeprom.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/myeeprom.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/myeeprom.h 2017-12-17 16:22:27.000000000 +0000 @@ -48,6 +48,7 @@ #endif #define GET_PPM_POLARITY(idx) g_model.moduleData[idx].ppm.pulsePol +#define GET_SBUS_POLARITY(idx) g_model.moduleData[idx].sbus.noninverted #define GET_PPM_DELAY(idx) (g_model.moduleData[idx].ppm.delay * 50 + 300) #define SET_DEFAULT_PPM_FRAME_LENGTH(idx) g_model.moduleData[idx].ppm.frameLength = 4 * max((int8_t)0, g_model.moduleData[idx].channelsCount) @@ -106,6 +107,8 @@ #define CFN_RESET(p) ((p)->active=0, (p)->clear.val1=0, (p)->clear.val2=0) #define CFN_GVAR_CST_MIN -GVAR_MAX #define CFN_GVAR_CST_MAX GVAR_MAX +#define MODEL_GVAR_MIN(idx) (CFN_GVAR_CST_MIN + g_model.gvars[idx].min) +#define MODEL_GVAR_MAX(idx) (CFN_GVAR_CST_MAX - g_model.gvars[idx].max) #elif defined(CPUM2560) #define CFN_SWITCH(p) ((p)->swtch) #define CFN_FUNC(p) ((p)->func) @@ -473,7 +476,7 @@ PROTO_DSM2_DSM2, PROTO_DSM2_DSMX, #endif -#if defined(CROSSFIRE) || defined(MULTIMODULE) +#if defined(CPUARM) PROTO_CROSSFIRE, #endif #if defined(IRPROTOS) @@ -484,14 +487,15 @@ PROTO_PICZ, PROTO_SWIFT, #endif -#if defined(MULTIMODULE) +#if defined(CPUARM) PROTO_MULTIMODULE, + PROTO_SBUS, #endif PROTO_MAX, PROTO_NONE }; -enum RFProtocols { +enum XJTRFProtocols { RF_PROTO_OFF = -1, RF_PROTO_X16, RF_PROTO_D8, @@ -499,6 +503,12 @@ RF_PROTO_LAST = RF_PROTO_LR12 }; +enum R9MSubTypes +{ + MODULE_SUBTYPE_R9M_FCC, + MODULE_SUBTYPE_R9M_LBT, +}; + enum MultiModuleRFProtocols { MM_RF_PROTO_CUSTOM = -1, MM_RF_PROTO_FIRST = MM_RF_PROTO_CUSTOM, @@ -533,7 +543,10 @@ MM_RF_PROTO_Q303, MM_RF_PROTO_GW008, MM_RF_PROTO_DM002, - MM_RF_PROTO_LAST= MM_RF_PROTO_DM002 + MM_RF_PROTO_CABELL, + MM_RF_PROTO_ESKY150, + MM_RF_PROTO_H83D, + MM_RF_PROTO_LAST= MM_RF_PROTO_H83D }; enum MMDSM2Subtypes { @@ -569,6 +582,8 @@ MODULE_TYPE_DSM2, MODULE_TYPE_CROSSFIRE, MODULE_TYPE_MULTIMODULE, + MODULE_TYPE_R9M, + MODULE_TYPE_SBUS, MODULE_TYPE_COUNT }; @@ -577,8 +592,6 @@ XJT_EXTERNAL_ANTENNA }; -#define IS_EXTERNAL_MODULE_PRESENT() (g_model.moduleData[EXTERNAL_MODULE].type != MODULE_TYPE_NONE) - enum FailsafeModes { FAILSAFE_NOT_SET, FAILSAFE_HOLD, diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/opentx.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/opentx.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/opentx.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/opentx.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -252,23 +252,29 @@ g_eeGeneral.potsConfig = 0x05; // S1 and S2 = pots with detent g_eeGeneral.slidersConfig = 0x03; // LS and RS = sliders with detent #endif - + #if defined(PCBX7) g_eeGeneral.switchConfig = 0x000006ff; // 4x3POS, 1x2POS, 1xTOGGLE #elif defined(PCBTARANIS) || defined(PCBHORUS) g_eeGeneral.switchConfig = 0x00007bff; // 6x3POS, 1x2POS, 1xTOGGLE #endif -#if defined(PCBX9E) +// vBatWarn is voltage in 100mV, vBatMin is in 100mV but with -9V offset, vBatMax has a -12V offset +#if defined(PCBX9E) || defined(PCBX12S) // NI-MH 9.6V g_eeGeneral.vBatWarn = 87; - g_eeGeneral.vBatMin = -5; - g_eeGeneral.vBatMax = -5; + g_eeGeneral.vBatMin = -5; //8,5V + g_eeGeneral.vBatMax = -5; //11,5V +#elif defined(PCBX10) + // Lipo 2V + g_eeGeneral.vBatWarn = 66; + g_eeGeneral.vBatMin = -28; // 6.2V + g_eeGeneral.vBatMax = -38; // 8.2V #elif defined(PCBTARANIS) - // NI-MH 7.2V + // NI-MH 7.2V, X9D, X9D+ and X7 g_eeGeneral.vBatWarn = 65; - g_eeGeneral.vBatMin = -30; - g_eeGeneral.vBatMax = -40; + g_eeGeneral.vBatMin = -30; //6V + g_eeGeneral.vBatMax = -40; //8V #else g_eeGeneral.vBatWarn = 90; #endif @@ -398,18 +404,45 @@ void checkModelIdUnique(uint8_t index, uint8_t module) { uint8_t modelId = g_model.header.modelId[module]; + uint8_t additionalOnes = 0; + char * name = reusableBuffer.msgbuf.msg; + + memset(reusableBuffer.msgbuf.msg, 0, sizeof(reusableBuffer.msgbuf.msg)); + if (modelId != 0) { - for (uint8_t i=0; i (signed)(modelHeaders[i].name[0] ? zlen(modelHeaders[i].name, LEN_MODEL_NAME) : sizeof(TR_MODEL) + 2)) { // you cannot rely exactly on WARNING_LINE_LEN so using WARNING_LINE_LEN-2 (-2 for the ",") + if (reusableBuffer.msgbuf.msg[0] != 0) { + name = strAppend(name, ", "); + } + if (modelHeaders[i].name[0] == 0) { + name = strAppend(name, STR_MODEL); + name = strAppendUnsigned(name+strlen(name),i, 2); + } + else { + name += zchar2str(name, modelHeaders[i].name, LEN_MODEL_NAME); + } + } + else { + additionalOnes++; } } } } } + + if (additionalOnes) { + name = strAppend(name, " (+"); + name = strAppendUnsigned(name, additionalOnes); + name = strAppend(name, ")"); + } + + if (reusableBuffer.msgbuf.msg[0] != 0) { + POPUP_WARNING(STR_MODELIDUSED); + SET_WARNING_INFO(reusableBuffer.msgbuf.msg, sizeof(reusableBuffer.msgbuf.msg), 0); + } } #endif @@ -973,7 +1006,7 @@ drawSecondSplash(); } #endif - + #if defined(PCBSKY9X) if (curTime < get_tmr10ms()) { curTime += 10; @@ -1024,7 +1057,7 @@ void checkFailsafe() { for (int i=0; i 0 + pwmCheck(); +#endif + if (!unexpectedShutdown) { opentxStart(); } @@ -2599,6 +2657,10 @@ boardInit(); +#if defined(PCBX7) + bluetoothInit(BLUETOOTH_DEFAULT_BAUDRATE); //BT is turn on for a brief period to differentiate X7 and X7S +#endif + #if defined(GUI) && !defined(PCBTARANIS) && !defined(PCBFLAMENCO) && !defined(PCBHORUS) // TODO remove this lcdInit(); @@ -2719,6 +2781,8 @@ uint32_t pwrCheck() { + const char * message = NULL; + enum PwrCheckState { PWR_CHECK_ON, PWR_CHECK_OFF, @@ -2731,11 +2795,17 @@ return e_power_off; } else if (pwrPressed()) { + if (TELEMETRY_STREAMING()) { + message = STR_MODEL_STILL_POWERED; + } if (pwr_check_state == PWR_CHECK_PAUSED) { // nothing } else if (pwr_press_time == 0) { pwr_press_time = get_tmr10ms(); + if (message && !g_eeGeneral.disableRssiPoweroffAlarm) { + audioEvent(AU_MODEL_STILL_POWERED); + } } else { inactivity.counter = 0; @@ -2745,13 +2815,16 @@ if (get_tmr10ms() - pwr_press_time > PWR_PRESS_SHUTDOWN_DELAY) { #if defined(SHUTDOWN_CONFIRMATION) while (1) { +#else + while ((TELEMETRY_STREAMING() && !g_eeGeneral.disableRssiPoweroffAlarm)) { +#endif lcdRefreshWait(); lcdClear(); POPUP_CONFIRMATION("Confirm Shutdown"); event_t evt = getEvent(false); DISPLAY_WARNING(evt); lcdRefresh(); - if (warningResult == true) { + if (warningResult) { pwr_check_state = PWR_CHECK_OFF; return e_power_off; } @@ -2761,14 +2834,12 @@ return e_power_on; } } -#else haptic.play(15, 3, PLAY_NOW); pwr_check_state = PWR_CHECK_OFF; return e_power_off; -#endif } else { - drawShutdownAnimation(pwrPressedDuration()); + drawShutdownAnimation(pwrPressedDuration(), message); return e_power_press; } } @@ -2784,18 +2855,37 @@ uint32_t pwrCheck() { #if defined(SOFT_PWR_CTRL) - if (pwrPressed()) + if (pwrPressed()) { return e_power_on; + } #endif - if (usbPlugged()) + if (usbPlugged()) { return e_power_usb; + } #if defined(TRAINER_PWR) - if (TRAINER_CONNECTED()) + if (TRAINER_CONNECTED()) { return e_power_trainer; + } #endif + if (!g_eeGeneral.disableRssiPoweroffAlarm) { + if (TELEMETRY_STREAMING()) { + RAISE_ALERT(STR_MODEL, STR_MODEL_STILL_POWERED, STR_PRESS_ENTER_TO_CONFIRM, AU_MODEL_STILL_POWERED); + while (TELEMETRY_STREAMING()) { + resetForcePowerOffRequest(); + CoTickDelay(10); + if (pwrPressed()) { + return e_power_on; + } + else if (readKeys() == (1 << KEY_ENTER)) { + return e_power_off; + } + } + } + } + return e_power_off; } #endif diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/opentx.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/opentx.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/opentx.h 2017-05-14 17:18:57.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/opentx.h 2017-12-17 16:22:27.000000000 +0000 @@ -50,6 +50,12 @@ #define IF_CPUARM(x) #endif +#if defined(STM32) + #define CASE_STM32(x) x, +#else + #define CASE_STM32(x) +#endif + #if defined(VARIO) && defined(CPUARM) #define CASE_VARIO_CPUARM(x) x, #else @@ -146,7 +152,7 @@ #define CASE_SDCARD(x) #endif -#if defined(BLUETOOTH) +#if defined(BLUETOOTH) && !(defined(PCBX9E) && !defined(USEHORUSBT)) #define CASE_BLUETOOTH(x) x, #else #define CASE_BLUETOOTH(x) @@ -194,6 +200,18 @@ #define CASE_PCBX9E(x) #endif +#if defined(PCBX10) + #define CASE_PCBX10(x) x, +#else + #define CASE_PCBX10(x) +#endif + +#if defined(BLUETOOTH) && !(defined(PCBX9E) && !defined(USEHORUSBT)) + #define CASE_BLUETOOTH(x) x, +#else + #define CASE_BLUETOOTH(x) +#endif + #if defined(PCBSKY9X) && !defined(AR9X) && !defined(REVA) #define TX_CAPACITY_MEASUREMENT #define CASE_CAPACITY(x) x, @@ -218,6 +236,19 @@ #define IS_FAI_FORBIDDEN(idx) (IS_FAI_ENABLED() && idx >= MIXSRC_FIRST_TELEM) +#if defined(BLUETOOTH) +#if defined(X9E) && !defined(USEHORUSBT) + #define IS_BLUETOOTH_TRAINER() (g_model.trainerMode == TRAINER_MODE_SLAVE_BLUETOOTH) + #define IS_SLAVE_TRAINER() (g_model.trainerMode == TRAINER_MODE_SLAVE) +#else + #define IS_BLUETOOTH_TRAINER() (g_model.trainerMode == TRAINER_MODE_MASTER_BLUETOOTH || g_model.trainerMode == TRAINER_MODE_SLAVE_BLUETOOTH) + #define IS_SLAVE_TRAINER() (g_model.trainerMode == TRAINER_MODE_SLAVE || g_model.trainerMode == TRAINER_MODE_SLAVE_BLUETOOTH) +#endif +#else + #define IS_BLUETOOTH_TRAINER() false + #define IS_SLAVE_TRAINER() (g_model.trainerMode == TRAINER_MODE_SLAVE) +#endif + #if defined(CPUARM) #define MASTER_VOLUME #endif @@ -329,12 +360,12 @@ #define IF_ROTARY_ENCODERS(x) #endif -#define PPM_CENTER 1500 +#define PPM_CENTER 1500 #if defined(PPM_CENTER_ADJUSTABLE) - #define PPM_CH_CENTER(ch) (PPM_CENTER+limitAddress(ch)->ppmCenter) + #define PPM_CH_CENTER(ch) (PPM_CENTER + limitAddress(ch)->ppmCenter) #else - #define PPM_CH_CENTER(ch) (PPM_CENTER) + #define PPM_CH_CENTER(ch) (PPM_CENTER) #endif #if defined(CPUARM) @@ -342,7 +373,7 @@ #include "io/io_arm.h" // This doesn't need protection on this processor extern volatile tmr10ms_t g_tmr10ms; - #define get_tmr10ms() g_tmr10ms + #define get_tmr10ms() g_tmr10ms #else extern volatile tmr10ms_t g_tmr10ms; extern inline uint16_t get_tmr10ms() @@ -373,12 +404,14 @@ #include "pulses/pulses.h" #if defined(CPUARM) -// Order is the same as in enum Protocols in myeeprom.h (none, ppm, xjt, dsm, crossfire, multi) - static const int8_t maxChannelsModules[] = { 0, 8, 8, -2, 8, 4 }; // relative to 8! +// Order is the same as in enum Protocols in myeeprom.h (none, ppm, xjt, dsm, crossfire, multi, r9m, sbus) + static const int8_t maxChannelsModules[] = { 0, 8, 8, -2, 8, 4, 8, 8}; // relative to 8! static const int8_t maxChannelsXJT[] = { 0, 8, 0, 4 }; // relative to 8! #define MAX_TRAINER_CHANNELS_M8() (MAX_TRAINER_CHANNELS-8) #endif + + #if defined(MULTIMODULE) #define IS_MODULE_MULTIMODULE(idx) (idx==EXTERNAL_MODULE && g_model.moduleData[EXTERNAL_MODULE].type==MODULE_TYPE_MULTIMODULE) #else @@ -388,16 +421,11 @@ #if defined(PCBTARANIS) || defined(PCBHORUS) #if defined(TARANIS_INTERNAL_PPM) #define IS_MODULE_PPM(idx) (idx==TRAINER_MODULE || (idx==INTERNAL_MODULE && g_model.moduleData[INTERNAL_MODULE].type==MODULE_TYPE_PPM)|| (idx==EXTERNAL_MODULE && g_model.moduleData[EXTERNAL_MODULE].type==MODULE_TYPE_PPM)) - #define IS_MODULE_XJT(idx) (((idx==INTERNAL_MODULE && g_model.moduleData[INTERNAL_MODULE].type==MODULE_TYPE_XJT)|| (idx==EXTERNAL_MODULE && g_model.moduleData[EXTERNAL_MODULE].type==MODULE_TYPE_XJT)) && (g_model.moduleData[idx].rfProtocol != RF_PROTO_OFF)) #else #define IS_MODULE_PPM(idx) (idx==TRAINER_MODULE || (idx==EXTERNAL_MODULE && g_model.moduleData[EXTERNAL_MODULE].type==MODULE_TYPE_PPM)) - #define IS_MODULE_XJT(idx) ((idx==INTERNAL_MODULE || g_model.moduleData[EXTERNAL_MODULE].type==MODULE_TYPE_XJT) && (g_model.moduleData[idx].rfProtocol != RF_PROTO_OFF)) - #endif - #if defined(DSM2) - #define IS_MODULE_DSM2(idx) (idx==EXTERNAL_MODULE && g_model.moduleData[EXTERNAL_MODULE].type==MODULE_TYPE_DSM2) - #else - #define IS_MODULE_DSM2(idx) (false) #endif + #define IS_MODULE_XJT(idx) (g_model.moduleData[idx].type==MODULE_TYPE_XJT) + #if defined(CROSSFIRE) #define IS_MODULE_CROSSFIRE(idx) (idx==EXTERNAL_MODULE && g_model.moduleData[EXTERNAL_MODULE].type==MODULE_TYPE_CROSSFIRE) #else @@ -414,7 +442,6 @@ #elif defined(PCBSKY9X) && !defined(REVA) #define IS_MODULE_PPM(idx) (idx==TRAINER_MODULE || idx==EXTRA_MODULE || (idx==EXTERNAL_MODULE && g_model.moduleData[EXTERNAL_MODULE].type==MODULE_TYPE_PPM)) #define IS_MODULE_XJT(idx) (idx==EXTERNAL_MODULE && g_model.moduleData[EXTERNAL_MODULE].type==MODULE_TYPE_XJT) - #define IS_MODULE_DSM2(idx) (idx==EXTERNAL_MODULE && g_model.moduleData[EXTERNAL_MODULE].type==MODULE_TYPE_DSM2) #define MAX_EXTERNAL_MODULE_CHANNELS() ((g_model.moduleData[EXTERNAL_MODULE].type == MODULE_TYPE_XJT) ? maxChannelsXJT[1+g_model.moduleData[0].rfProtocol] : maxChannelsModules[g_model.moduleData[EXTERNAL_MODULE].type]) #define MAX_EXTRA_MODULE_CHANNELS() (8) // Only PPM (16ch PPM) #define MAX_CHANNELS(idx) (idx==EXTERNAL_MODULE ? MAX_EXTERNAL_MODULE_CHANNELS() : (idx==EXTRA_MODULE ? MAX_EXTRA_MODULE_CHANNELS() : MAX_TRAINER_CHANNELS_M8())) @@ -423,11 +450,22 @@ #else #define IS_MODULE_PPM(idx) (idx==TRAINER_MODULE || (idx==EXTERNAL_MODULE && g_model.moduleData[EXTERNAL_MODULE].type==MODULE_TYPE_PPM)) #define IS_MODULE_XJT(idx) (idx==EXTERNAL_MODULE && g_model.moduleData[EXTERNAL_MODULE].type==MODULE_TYPE_XJT) - #define IS_MODULE_DSM2(idx) (idx==EXTERNAL_MODULE && g_model.moduleData[EXTERNAL_MODULE].type==MODULE_TYPE_DSM2) #define MAX_EXTERNAL_MODULE_CHANNELS() ((g_model.moduleData[EXTERNAL_MODULE].type == MODULE_TYPE_XJT) ? maxChannelsXJT[1+g_model.moduleData[EXTERNAL_MODULE].rfProtocol] : maxChannelsModules[g_model.moduleData[EXTERNAL_MODULE].type]) #define MAX_CHANNELS(idx) (idx==EXTERNAL_MODULE ? MAX_EXTERNAL_MODULE_CHANNELS() : MAX_TRAINER_CHANNELS_M8()) #define NUM_CHANNELS(idx) (8+g_model.moduleData[idx].channelsCount) #endif +#define IS_MODULE_R9M(idx) (g_model.moduleData[idx].type == MODULE_TYPE_R9M) +#define IS_MODULE_R9M_FCC(idx) (IS_MODULE_R9M(idx) && g_model.moduleData[idx].subType == MODULE_SUBTYPE_R9M_FCC) +#define IS_MODULE_R9M_LBT(idx) (IS_MODULE_R9M(idx) && g_model.moduleData[idx].subType == MODULE_SUBTYPE_R9M_LBT) +#define IS_MODULE_PXX(idx) (IS_MODULE_XJT(idx) || IS_MODULE_R9M(idx)) + +#if defined(DSM2) + #define IS_MODULE_DSM2(idx) (idx==EXTERNAL_MODULE && g_model.moduleData[EXTERNAL_MODULE].type==MODULE_TYPE_DSM2) + #define IS_MODULE_SBUS(idx) (idx==EXTERNAL_MODULE && g_model.moduleData[EXTERNAL_MODULE].type==MODULE_TYPE_SBUS) +#else + #define IS_MODULE_DSM2(idx) (false) +#endif + #if defined(MULTIMODULE) #define IS_MULTIMODULE_DSM(idx) (IS_MODULE_MULTIMODULE(idx) && g_model.moduleData[idx].getMultiProtocol(true) == MM_RF_PROTO_DSM2) @@ -1231,6 +1269,7 @@ AU_SENSOR_LOST, AU_SERVO_KO, AU_RX_OVERLOAD, + AU_MODEL_STILL_POWERED, #endif #if defined(PCBSKY9X) AU_TX_MAH_HIGH, @@ -1256,6 +1295,10 @@ AU_POT2_MIDDLE, AU_SLIDER1_MIDDLE, AU_SLIDER2_MIDDLE, +#if defined(PCBX9E) + AU_SLIDER3_MIDDLE, + AU_SLIDER4_MIDDLE, +#endif #elif defined(CPUARM) AU_POT1_MIDDLE, AU_POT2_MIDDLE, @@ -1373,7 +1416,9 @@ // 275 bytes struct { +#if !defined(CPUARM) char listnames[NUM_BODY_LINES][LEN_MODEL_NAME]; +#endif #if defined(EEPROM_RLC) && LCD_W < 212 uint16_t eepromfree; #endif @@ -1385,6 +1430,10 @@ #endif } modelsel; + struct { + char msg[64]; + } msgbuf; // used in modelsel and modelsetup (only in a warning message) + // 103 bytes struct { @@ -1528,7 +1577,9 @@ } #if defined(TELEMETRY_FRSKY) +#if !defined(CPUARM) NOINLINE uint8_t getRssiAlarmValue(uint8_t alarm); +#endif extern const pm_uint8_t bchunit_ar[]; @@ -1631,7 +1682,7 @@ extern const pm_uchar logo_taranis[]; #endif -#if defined(USB_MASS_STORAGE) +#if defined(STM32) void usbPluggedIn(); #endif @@ -1688,4 +1739,8 @@ #include "gps.h" #endif +#if defined(BLUETOOTH) +#include "bluetooth.h" +#endif + #endif // _OPENTX_H_ diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/pulses/multi_arm.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/pulses/multi_arm.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/pulses/multi_arm.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/pulses/multi_arm.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -26,93 +26,129 @@ -/* The protocol is heavily inspired by the DSM2 protocol, so reuse some the definitions where they are identical */ - #define MULTI_SEND_BIND (1 << 7) #define MULTI_SEND_RANGECHECK (1 << 5) #define MULTI_SEND_AUTOBIND (1 << 6) -#define BITLEN_MULTI (10*2) //100000 Baud => 10uS per bit +#define MULTI_CHANS 16 +#define MULTI_CHAN_BITS 11 -#if defined(PPM_PIN_SERIAL) -static void sendByteMulti(uint8_t b) -{ - uint8_t parity = 1; +static void sendFrameProtocolHeader(uint8_t port, bool failsafe); - putDsm2SerialBit(0); // Start bit - for (uint8_t i=0; i<8; i++) { // 8 data Bits - putDsm2SerialBit(b & 1); - parity = parity ^ (b & 1); - b >>= 1; - } - putDsm2SerialBit(!parity); // Even Parity bit +void sendChannels(uint8_t port); - putDsm2SerialBit(1); // Stop bit - putDsm2SerialBit(1); // Stop bit -} -#else -static void _send_level(uint8_t v) +static void sendSetupFrame() { - /* Copied over from DSM, this looks doubious and in my logic analyzer - output the low->high is about 2 ns late */ - if (modulePulsesData[EXTERNAL_MODULE].dsm2.index & 1) - v += 2; - else - v -= 2; - *modulePulsesData[EXTERNAL_MODULE].dsm2.ptr++ = v - 1; - modulePulsesData[EXTERNAL_MODULE].dsm2.index+=1; - modulePulsesData[EXTERNAL_MODULE].dsm2.rest -=v; + // Old multi firmware will mark config messsages as invalid frame and throw them away + sendByteSbus('M'); + sendByteSbus('P'); + sendByteSbus(0x80); // Module Configuration + sendByteSbus(1); // 1 byte data + uint8_t config = 0x1 | 0x2; // inversion + multi_telemetry +#if !defined(PPM_PIN_SERIAL) + config |= 0x04; //input synchronsisation +#endif + + sendByteSbus(config); } -static void sendByteMulti(uint8_t b) //max 11 changes 0 10 10 10 10 P 1 +static void sendFailsafeChannels(uint8_t port) { - bool lev = 0; - uint8_t parity = 1; + uint32_t bits = 0; + uint8_t bitsavailable = 0; + + for (int i = 0; i < MULTI_CHANS; i++) { + int16_t failsafeValue = g_model.moduleData[port].failsafeChannels[i]; + int pulseValue; + if (g_model.moduleData[port].failsafeMode == FAILSAFE_HOLD) + failsafeValue = FAILSAFE_CHANNEL_HOLD; + + if (g_model.moduleData[port].failsafeMode == FAILSAFE_NOPULSES) + failsafeValue = FAILSAFE_CHANNEL_NOPULSE; - uint8_t len = BITLEN_MULTI; //max val: 10*20 < 256 - for (uint8_t i=0; i<=9; i++) { //8Bits + 1Parity + Stop=1 - bool nlev = b & 1; //lsb first - parity = parity ^ (uint8_t)nlev; - if (lev == nlev) { - len += BITLEN_MULTI; + + if (failsafeValue == FAILSAFE_CHANNEL_HOLD) { + pulseValue = 0; + } + else if (failsafeValue == FAILSAFE_CHANNEL_NOPULSE) { + pulseValue = 2047; } else { - _send_level(len); - len = BITLEN_MULTI; - lev = nlev; - } - b = (b>>1) | 0x80; //shift in ones for stop bit and parity - if (i==7) - b = b ^ parity; // lowest bit is one from previous line - } - _send_level(len+ BITLEN_MULTI); // enlarge the last bit to be two stop bits long -} -#endif - -// This is the data stream to send, prepare after 19.5 mS -// Send after 22.5 mS + failsafeValue += 2 * PPM_CH_CENTER(g_model.moduleData[port].channelsStart + i) - 2 * PPM_CENTER; + pulseValue = limit(1, (failsafeValue * 800 / 1000) + 1024, 2047); + } -//static uint8_t *Dsm2_pulsePtr = pulses2MHz.pbyte ; + bits |= pulseValue << bitsavailable; + bitsavailable += MULTI_CHAN_BITS; + while (bitsavailable >= 8) { + sendByteSbus((uint8_t) (bits & 0xff)); + bits >>= 8; + bitsavailable -= 8; + } + } +} -#define MULTI_CHANS 16 -#define MULTI_CHAN_BITS 11 void setupPulsesMultimodule(uint8_t port) { + static int counter=0; #if defined(PPM_PIN_SERIAL) modulePulsesData[EXTERNAL_MODULE].dsm2.serialByte = 0 ; modulePulsesData[EXTERNAL_MODULE].dsm2.serialBitCount = 0 ; #else - modulePulsesData[EXTERNAL_MODULE].dsm2.rest = 18000; // 9ms refresh + modulePulsesData[EXTERNAL_MODULE].dsm2.rest = multiSyncStatus.getAdjustedRefreshRate(); modulePulsesData[EXTERNAL_MODULE].dsm2.index = 0; #endif modulePulsesData[EXTERNAL_MODULE].dsm2.ptr = modulePulsesData[EXTERNAL_MODULE].dsm2.pulses; + // Every 1000 cycles (=9s) send a config packet that configures the multimodule (inversion, telemetry type) + counter++; + if (counter % 1000== 500) { + sendSetupFrame(); + } else if (counter % 1000 == 0 && g_model.moduleData[port].failsafeMode != FAILSAFE_NOT_SET && g_model.moduleData[port].failsafeMode != FAILSAFE_RECEIVER) { + sendFrameProtocolHeader(port, true); + sendFailsafeChannels(port); + } else { + // Normal Frame + sendFrameProtocolHeader(port, false); + sendChannels(port); + } + + putDsm2Flush(); +} - // byte 1+2, protocol information + +void sendChannels(uint8_t port) +{ + uint32_t bits = 0; + uint8_t bitsavailable = 0; + + // byte 4-25, channels 0..2047 + // Range for pulses (channelsOutputs) is [-1024:+1024] for [-100%;100%] + // Multi uses [204;1843] as [-100%;100%] + for (int i = 0; i < MULTI_CHANS; i++) { + int channel = g_model.moduleData[port].channelsStart + i; + int value = channelOutputs[channel] + 2 * PPM_CH_CENTER(channel) - 2 * PPM_CENTER; + + // Scale to 80% + value = value * 800 / 1000 + 1024; + value = limit(0, value, 2047); + + bits |= value << bitsavailable; + bitsavailable += MULTI_CHAN_BITS; + while (bitsavailable >= 8) { + sendByteSbus((uint8_t) (bits & 0xff)); + bits >>= 8; + bitsavailable -= 8; + } + } +} + +void sendFrameProtocolHeader(uint8_t port, bool failsafe) +{// byte 1+2, protocol information // Our enumeration starts at 0 int type = g_model.moduleData[port].getMultiProtocol(false) + 1; @@ -126,10 +162,10 @@ protoByte |= MULTI_SEND_RANGECHECK; // rfProtocol - if (g_model.moduleData[port].getMultiProtocol(true) == MM_RF_PROTO_DSM2){ + if (g_model.moduleData[port].getMultiProtocol(true) == MM_RF_PROTO_DSM2) { // Autobinding should always be done in DSMX 11ms - if(g_model.moduleData[port].multi.autoBindMode && moduleFlag[port] == MODULE_BIND) + if (g_model.moduleData[port].multi.autoBindMode && moduleFlag[port] == MODULE_BIND) subtype = MM_RF_DSM2_SUBTYPE_AUTO; // Multi module in DSM mode wants the number of channels to be used as option value @@ -144,10 +180,10 @@ // 25 is again a FrSky protocol (FrskyV) so shift again if (type >= 25) - type = type + 1; + type = type + 1; if (g_model.moduleData[port].getMultiProtocol(true) == MM_RF_PROTO_FRSKY) { - if(subtype == MM_RF_FRSKY_SUBTYPE_D8) { + if (subtype == MM_RF_FRSKY_SUBTYPE_D8) { //D8 type = 3; subtype = 0; @@ -178,49 +214,30 @@ type = g_model.moduleData[port].getMultiProtocol(false); - // header, byte 0, 0x55 for proto 0-31 0x54 for 32-63 + uint8_t headerByte = 0x54; + if (failsafe) + headerByte = 0x56; + + // header, byte 0, 0x55 for proto 0-31 0x54 for 32-63 if (type <= 31) - sendByteMulti(0x55); + sendByteSbus(headerByte+1); else - sendByteMulti(0x54); + sendByteSbus(headerByte); // protocol byte protoByte |= (type & 0x1f); - if(g_model.moduleData[port].getMultiProtocol(true) != MM_RF_PROTO_DSM2) + if (g_model.moduleData[port].getMultiProtocol(true) != MM_RF_PROTO_DSM2) protoByte |= (g_model.moduleData[port].multi.autoBindMode << 6); - sendByteMulti(protoByte); + sendByteSbus(protoByte); // byte 2, subtype, powermode, model id - sendByteMulti((uint8_t) ((g_model.header.modelId[port] & 0x0f) + sendByteSbus((uint8_t) ((g_model.header.modelId[port] & 0x0f) | ((subtype & 0x7) << 4) | (g_model.moduleData[port].multi.lowPowerMode << 7)) - ); + ); // byte 3 - sendByteMulti((uint8_t) optionValue); - - uint32_t bits = 0; - uint8_t bitsavailable = 0; - - // byte 4-25, channels 0..2047 - // Range for pulses (channelsOutputs) is [-1024:+1024] for [-100%;100%] - // Multi uses [204;1843] as [-100%;100%] - for (int i=0; i= 8) { - sendByteMulti((uint8_t) (bits & 0xff)); - bits >>= 8; - bitsavailable -= 8; - } - } - - putDsm2Flush(); + sendByteSbus((uint8_t) optionValue); } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/pulses/pulses_arm.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/pulses/pulses_arm.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/pulses/pulses_arm.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/pulses/pulses_arm.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -39,11 +39,12 @@ switch (port) { #if defined(PCBTARANIS) || defined(PCBHORUS) case INTERNAL_MODULE: -#if defined(TARANIS_INTERNAL_PPM) switch (g_model.moduleData[INTERNAL_MODULE].type) { +#if defined(TARANIS_INTERNAL_PPM) case MODULE_TYPE_PPM: required_protocol = PROTO_PPM; break; +#endif case MODULE_TYPE_XJT: required_protocol = PROTO_PXX; break; @@ -51,9 +52,6 @@ required_protocol = PROTO_NONE; break; } -#else - required_protocol = g_model.moduleData[INTERNAL_MODULE].rfProtocol == RF_PROTO_OFF ? PROTO_NONE : PROTO_PXX; -#endif break; #endif @@ -64,8 +62,12 @@ required_protocol = PROTO_PPM; break; case MODULE_TYPE_XJT: + case MODULE_TYPE_R9M: required_protocol = PROTO_PXX; break; + case MODULE_TYPE_SBUS: + required_protocol = PROTO_SBUS; + break; #if defined(MULTIMODULE) case MODULE_TYPE_MULTIMODULE: required_protocol = PROTO_MULTIMODULE; @@ -146,9 +148,10 @@ #if defined(MULTIMODULE) case PROTO_MULTIMODULE: - disable_multimodule(port); - break; #endif + case PROTO_SBUS: + disable_sbusOut(port); + break; case PROTO_PPM: disable_ppm(port); @@ -167,6 +170,10 @@ setupPulsesPXX(port); scheduleNextMixerCalculation(port, 9); break; + case PROTO_SBUS: + setupPulsesSbus(port); + scheduleNextMixerCalculation(port, (45+g_model.moduleData[port].sbus.refreshRate)/2); + break; #if defined(DSM2) case PROTO_DSM2_LP45: @@ -241,9 +248,11 @@ #if defined(MULTIMODULE) case PROTO_MULTIMODULE: - init_multimodule(port); - break; #endif + case PROTO_SBUS: + init_sbusOut(port); + break; + case PROTO_PPM: init_ppm(port); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/pulses/pulses_arm.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/pulses/pulses_arm.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/pulses/pulses_arm.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/pulses/pulses_arm.h 2017-12-17 16:22:27.000000000 +0000 @@ -27,7 +27,7 @@ #define MODULES_INIT(...) __VA_ARGS__ #endif -#if defined(PCBHORUS) && PCBREV < 13 +#if defined(PCBX12S) && PCBREV < 13 #define pulse_duration_t uint32_t #define trainer_pulse_duration_t uint16_t #else @@ -79,6 +79,7 @@ /* DSM2 uses 2 header + 12 channel bytes, with max 10 changes (8n2) per byte + 16 bits trailer ~= 156 max pulses */ /* Multimodule uses 3 bytes header + 22 channel bytes with max 11 changes per byte (8e2) + 16 bits trailer ~= 291 max pulses */ /* Multimodule reuses some of the DSM2 function and structs since the protocols are similar enough */ +/* sbus is 1 byte header, 22 channel bytes (11bit * 16ch) + 1 byte flags */ PACK(struct PxxTimerPulsesData { pulse_duration_t pulses[200]; pulse_duration_t * ptr; @@ -87,11 +88,7 @@ uint32_t pcmOnesCount; }); -#if defined(MULTIMODULE) #define MAX_PULSES_TRANSITIONS 300 -#else -#define MAX_PULSES_TRANSITIONS 200 -#endif PACK(struct Dsm2TimerPulsesData { pulse_duration_t pulses[MAX_PULSES_TRANSITIONS]; @@ -101,8 +98,6 @@ }); #endif -#define CROSSFIRE_BAUDRATE 400000 -#define CROSSFIRE_FRAME_PERIOD 4 // 4ms #define CROSSFIRE_FRAME_MAXLEN 64 #define CROSSFIRE_CHANNELS_COUNT 16 PACK(struct CrossfirePulsesData { @@ -130,6 +125,7 @@ * sizeof(ModulePulsesData). __ALIGNED is required for sizeof(ModulePulsesData) to be a multiple of the alignment. */ +/* TODO: internal pulsedata only needs 200 bytes vs 300 bytes for external, both use 300 byte since we have a common struct */ extern ModulePulsesData modulePulsesData[NUM_MODULES]; union TrainerPulsesData { @@ -142,12 +138,14 @@ void setupPulses(uint8_t port); void setupPulsesDSM2(uint8_t port); void setupPulsesMultimodule(uint8_t port); +void setupPulsesSbus(uint8_t port); void setupPulsesPXX(uint8_t port); void setupPulsesPPMModule(uint8_t port); void setupPulsesPPMTrainer(); void sendByteDsm2(uint8_t b); void putDsm2Flush(); void putDsm2SerialBit(uint8_t bit); +void sendByteSbus(uint8_t byte); #if defined(HUBSAN) void Hubsan_Init(); @@ -182,4 +180,28 @@ } } +#define LEN_R9M_MODES "\007" +#define TR_R9M_MODES "FCC\0 ""LBT(EU)" +#define LEN_R9M_FCC_POWER_VALUES "\006" +#define LEN_R9M_LBT_POWER_VALUES "\006" +#define TR_R9M_FCC_POWER_VALUES "10 mW\0" "100 mW" "500 mW" "1 W\0" +#define TR_R9M_LBT_POWER_VALUES "25 mW\0" "500 mW" + +enum R9MFCCPowerValues { + R9M_FCC_POWER_10 = 0, + R9M_FCC_POWER_100, + R9M_FCC_POWER_500, + R9M_FCC_POWER_1000, + R9M_FCC_POWER_MAX = R9M_FCC_POWER_1000 +}; + +enum R9MLBTPowerValues { + R9M_LBT_POWER_25 = 0, + R9M_LBT_POWER_500, + R9M_LBT_POWER_MAX = R9M_LBT_POWER_500 +}; + +#define BIND_TELEM_ALLOWED(idx) (!IS_MODULE_R9M_LBT(idx) || g_model.moduleData[idx].pxx.power == R9M_LBT_POWER_25) +#define BIND_CH9TO16_ALLOWED(idx) (!IS_MODULE_R9M_LBT(idx) || g_model.moduleData[idx].pxx.power != R9M_LBT_POWER_25) + #endif // _PULSES_ARM_H_ diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/pulses/pulses.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/pulses/pulses.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/pulses/pulses.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/pulses/pulses.h 2017-10-31 16:16:43.000000000 +0000 @@ -77,6 +77,12 @@ #define IS_MULTIMODULE_PROTOCOL(protocol) (0) #endif +#if defined(CPUARM) + #define IS_SBUS_PROTOCOL(protocol) (protocol == PROTO_SBUS) +#else + #define IS_SBUS_PROTOCOL(protocol) (0) +#endif + #if defined(CPUARM) #include "pulses_arm.h" diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/pulses/pxx_arm.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/pulses/pxx_arm.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/pulses/pxx_arm.cpp 2017-05-14 17:18:57.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/pulses/pxx_arm.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -372,29 +372,26 @@ pulseValueLow = pulseValue; } } -#if defined(BINDING_OPTIONS) + + uint8_t extra_flags = 0; + /* Ext. flag (holds antenna selection on Horus internal module, 0x00 otherwise) */ -uint8_t extra_flags = XJT_INTERNAL_ANTENNA; - if (port == INTERNAL_MODULE) { -#if defined(PCBHORUS) - extra_flags = g_model.moduleData[INTERNAL_MODULE].pxx.external_antenna; -#endif - extra_flags |= g_model.moduleData[INTERNAL_MODULE].pxx.receiver_telem_off << 1; - extra_flags |= g_model.moduleData[INTERNAL_MODULE].pxx.receiver_channel_9_16 << 2; -} -putPcmByte(port, extra_flags); -#else //BINDING_OPTIONS - /* Ext. flag (holds antenna selection on Horus internal module, 0x00 otherwise) */ #if defined(PCBHORUS) - uint8_t antenna = XJT_INTERNAL_ANTENNA; if (port == INTERNAL_MODULE) { - antenna = g_model.moduleData[INTERNAL_MODULE].pxx.external_antenna; + extra_flags |= (g_model.moduleData[port].pxx.external_antenna << 0); } - putPcmByte(port, antenna); -#else - putPcmByte(port, 0); -#endif #endif + extra_flags |= (g_model.moduleData[port].pxx.receiver_telem_off << 1); + extra_flags |= (g_model.moduleData[port].pxx.receiver_channel_9_16 << 2); + if (IS_MODULE_R9M(port)) { + extra_flags |= (min(g_model.moduleData[port].pxx.power, IS_MODULE_R9M_FCC(port) ? (uint8_t)R9M_FCC_POWER_MAX : (uint8_t)R9M_LBT_POWER_MAX) << 3); + // Disable S.PORT if internal module is active + if (IS_TELEMETRY_INTERNAL_MODULE() || !g_model.moduleData[port].pxx.sport_out) { + extra_flags |= (1 << 5); + } + } + + putPcmByte(port, extra_flags); /* CRC */ putPcmCrc(port); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/pulses/sbus_arm.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/pulses/sbus_arm.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/pulses/sbus_arm.cpp 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/pulses/sbus_arm.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -0,0 +1,157 @@ +/* + * Copyright (C) OpenTX + * + * Based on code named + * th9x - http://code.google.com/p/th9x + * er9x - http://code.google.com/p/er9x + * gruvin9x - http://code.google.com/p/gruvin9x + * + * License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + * + * 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. + */ + +#include "opentx.h" + + +#define BITLEN_SBUS (10*2) //100000 Baud => 10uS per bit + + +/* The protocol reuse some the DSM2 definitions where they are identical */ + + +#if defined(PPM_PIN_SERIAL) +void sendByteSbus(uint8_t b) +{ + uint8_t parity = 1; + + putDsm2SerialBit(0); // Start bit + for (uint8_t i=0; i<8; i++) { // 8 data Bits + putDsm2SerialBit(b & 1); + parity = parity ^ (b & 1); + b >>= 1; + } + putDsm2SerialBit(!parity); // Even Parity bit + + putDsm2SerialBit(1); // Stop bit + putDsm2SerialBit(1); // Stop bit +} +#else +static void _send_level(uint8_t v) +{ + /* Copied over from DSM, this looks doubious and in my logic analyzer + output the low->high is about 2 ns late */ + if (modulePulsesData[EXTERNAL_MODULE].dsm2.index & 1) + v += 2; + else + v -= 2; + + *modulePulsesData[EXTERNAL_MODULE].dsm2.ptr++ = v - 1; + modulePulsesData[EXTERNAL_MODULE].dsm2.index+=1; + modulePulsesData[EXTERNAL_MODULE].dsm2.rest -=v; +} + +void sendByteSbus(uint8_t b) //max 11 changes 0 10 10 10 10 P 1 +{ + bool lev = 0; + uint8_t parity = 1; + + uint8_t len = BITLEN_SBUS; //max val: 10*20 < 256 + for (uint8_t i=0; i<=9; i++) { //8Bits + 1Parity + Stop=1 + bool nlev = b & 1; //lsb first + parity = parity ^ (uint8_t)nlev; + if (lev == nlev) { + len += BITLEN_SBUS; + } + else { + _send_level(len); + len = BITLEN_SBUS; + lev = nlev; + } + b = (b>>1) | 0x80; //shift in ones for stop bit and parity + if (i==7) + b = b ^ parity; // lowest bit is one from previous line + } + _send_level(len+ BITLEN_SBUS); // enlarge the last bit to be two stop bits long +} +#endif + + + + +#define SBUS_NORMAL_CHANS 16 +#define SBUS_CHAN_BITS 11 + + +/* Definitions from CleanFlight/BetaFlight */ + +#define SBUS_FLAG_CHANNEL_17 (1 << 0) +#define SBUS_FLAG_CHANNEL_18 (1 << 1) +#define SBUS_FLAG_SIGNAL_LOSS (1 << 2) +#define SBUS_FLAG_FAILSAFE_ACTIVE (1 << 3) +#define SBUS_FRAME_BEGIN_BYTE 0x0F + +#define SBUS_CHAN_CENTER 992 + +inline int getChannelValue(uint8_t port, int channel) { + int ch = g_model.moduleData[port].channelsStart+channel; + // We will ignore 17 and 18th if that brings us over the limit + if (ch > 31) + return 0; + return channelOutputs[ch] + 2*PPM_CH_CENTER(ch) - 2*PPM_CENTER; +} + +void setupPulsesSbus(uint8_t port) +{ +#if defined(PPM_PIN_SERIAL) + modulePulsesData[EXTERNAL_MODULE].dsm2.serialByte = 0 ; + modulePulsesData[EXTERNAL_MODULE].dsm2.serialBitCount = 0 ; +#else + modulePulsesData[EXTERNAL_MODULE].dsm2.rest = (g_model.moduleData[EXTERNAL_MODULE].sbus.refreshRate * 5 + 225)*200 ; + modulePulsesData[EXTERNAL_MODULE].dsm2.index = 0; +#endif + + modulePulsesData[EXTERNAL_MODULE].dsm2.ptr = modulePulsesData[EXTERNAL_MODULE].dsm2.pulses; + + + // Sync Byte + sendByteSbus(SBUS_FRAME_BEGIN_BYTE); + + uint32_t bits = 0; + uint8_t bitsavailable = 0; + + // byte 1-22, channels 0..2047, limits not really clear (B + for (int i=0; i= 8) { + sendByteSbus((uint8_t) (bits & 0xff)); + bits >>= 8; + bitsavailable -= 8; + } + } + // Flags + uint8_t flags=0; + if (getChannelValue(port, 16) > 0) + flags |=SBUS_FLAG_CHANNEL_17; + if (getChannelValue(port, 17) > 0) + flags |=SBUS_FLAG_CHANNEL_18; + + sendByteSbus(flags); + + // Last byte, always 0x0 + sendByteSbus(0x0); + + putDsm2Flush(); + +} diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/rtc.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/rtc.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/rtc.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/rtc.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -473,7 +473,7 @@ gtime_t newTime = gmktime(&t) + g_eeGeneral.timezone * 3600; gtime_t diff = (g_rtcTime > newTime) ? (g_rtcTime - newTime) : (newTime - g_rtcTime); -#if defined(DEBUG) +#if defined(DEBUG) && defined (PCBTARANIS) struct gtm utm; rtcGetTime(&utm); gtime_t rtcTime = gmktime(&utm); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/sdcard.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/sdcard.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/sdcard.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/sdcard.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -22,6 +22,37 @@ #include "opentx.h" #include "diskio.h" +bool sdCardFormat() +{ + BYTE work[_MAX_SS]; + FRESULT res = f_mkfs("", FM_FAT32, 0, work, sizeof(work)); + switch(res) { + case FR_OK : + return true; + case FR_DISK_ERR: + POPUP_WARNING("Format error"); + return false; + case FR_NOT_READY: + POPUP_WARNING("SDCard not ready"); + return false; + case FR_WRITE_PROTECTED: + POPUP_WARNING("SDCard write protected"); + return false; + case FR_INVALID_PARAMETER: + POPUP_WARNING("Format param invalid"); + return false; + case FR_INVALID_DRIVE: + POPUP_WARNING("Invalid drive"); + return false; + case FR_MKFS_ABORTED: + POPUP_WARNING("Format aborted"); + return false; + default: + POPUP_WARNING(STR_SDCARD_ERROR); + return false; + } +} + const char * sdCheckAndCreateDirectory(const char * path) { DIR archiveFolder; @@ -472,7 +503,7 @@ uint32_t sdGetSize() { - return (sdGetNoSectors() * BLOCK_SIZE) / 1000000; + return (sdGetNoSectors() / 1000000) * BLOCK_SIZE; } uint32_t sdGetFreeSectors() diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/sdcard.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/sdcard.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/sdcard.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/sdcard.h 2017-12-17 16:22:27.000000000 +0000 @@ -40,7 +40,6 @@ #define LAYOUTS_PATH ROOT_PATH "LAYOUTS" #define WIDGETS_PATH ROOT_PATH "WIDGETS" #define WIZARD_NAME "wizard.lua" -#define TEMPLATES_PATH SCRIPTS_PATH "/TEMPLATES" #define SCRIPTS_MIXES_PATH SCRIPTS_PATH "/MIXES" #define SCRIPTS_FUNCS_PATH SCRIPTS_PATH "/FUNCTIONS" #define SCRIPTS_TELEM_PATH SCRIPTS_PATH "/TELEMETRY" @@ -96,6 +95,7 @@ void logsClose(); void logsWrite(); +bool sdCardFormat(); uint32_t sdGetNoSectors(); uint32_t sdGetSize(); uint32_t sdGetFreeSectors(); @@ -115,16 +115,19 @@ const char * getFileExtension(const char * filename, uint8_t size=0, uint8_t extMaxLen=0, uint8_t *fnlen=NULL, uint8_t *extlen=NULL); // TODO REMOVE THE O9X FOURCC in 2.3 -#if defined(PCBHORUS) - #define OTX_FOURCC 0x3478746F // otx for Horus +#if defined(PCBX12S) + #define OTX_FOURCC 0x3478746F // otx for X12S #define O9X_FOURCC 0x3178396F // we forgot it in 2.2 RC .. +#elif defined(PCBX10) + #define OTX_FOURCC 0x3778746F // otx for X10 + #define O9X_FOURCC 0x3478746F // match X12S, we forgot OTX_FOURCC before 2.2.1 RC2 #elif defined(PCBX9E) #define OTX_FOURCC 0x3578746F // otx for Taranis X9E #define O9X_FOURCC 0x3378396F // o9x for Taranis X9E #elif defined(PCBX7) #define OTX_FOURCC 0x3678746F // otx for Taranis X7 #define O9X_FOURCC 0x3378396F // o9x for Taranis X7 -#elif defined(PCBTARANIS) +#elif defined(PCBX9D) || defined(PCBX9DP) #define OTX_FOURCC 0x3378746F // otx for Taranis X9D #define O9X_FOURCC 0x3378396F // o9x for Taranis X9D #elif defined(PCBSKY9X) diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/serial.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/serial.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/serial.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/serial.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -2,7 +2,7 @@ * Copyright (C) OpenTX * * Based on code named - * th9x - http://code.google.com/p/th9x + * th9x - http://code.google.com/p/th9x * er9x - http://code.google.com/p/er9x * gruvin9x - http://code.google.com/p/gruvin9x * @@ -25,12 +25,12 @@ #define PRINTF_BUFFER_SIZE 128 -void serialPutc(char c) -{ -#if defined(USB_SERIAL) - usbSerialPutc(c); -#elif defined(SERIAL2) - serial2Putc(c); +void serialPutc(char c) { + if (getSelectedUsbMode() == USB_SERIAL_MODE) + usbSerialPutc(c); +#if defined(SERIAL2) + if (serial2TracesEnabled()) + serial2Putc(c); #endif } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/storage/eeprom_conversions.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/storage/eeprom_conversions.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/storage/eeprom_conversions.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/storage/eeprom_conversions.cpp 2017-11-15 20:54:40.000000000 +0000 @@ -436,8 +436,14 @@ FrSkyLineData_v216 lines[4]; } FrSkyScreenData_v216; + +PACK(struct FrSkyChannelData_v216 { + uint8_t unused[7]; +}); + + PACK(typedef struct { - FrSkyChannelData channels[4]; + FrSkyChannelData_v216 channels[4]; uint8_t usrProto; // Protocol in FrSky user data, 0=None, 1=FrSky hub, 2=WS HowHigh, 3=Halcyon uint8_t voltsSource:7; uint8_t altitudeDisplayed:1; @@ -450,7 +456,7 @@ int8_t varioCenterMin; int8_t varioMin; int8_t varioMax; - FrSkyRSSIAlarm rssiAlarms[2]; + uint8_t rssiAlarms[2]; uint16_t mAhPersistent:1; uint16_t storedMah:15; int8_t fasOffset; @@ -579,6 +585,12 @@ }) ModelData_v216; PACK(typedef struct { + char name[6]; + uint8_t popup:1; + uint8_t spare:7; +}) GVarData_v217; + +PACK(typedef struct { ModelHeader header; TimerData_v217 timers[MAX_TIMERS]; ARM_FIELD(uint8_t telemetryProtocol:3) @@ -610,9 +622,10 @@ swarnstate_t switchWarningState; swarnenable_t switchWarningEnable; - GVarData gvars[MAX_GVARS]; + GVarData_v217 gvars[MAX_GVARS]; FrSkyTelemetryData frsky; + RssiAlarmData rssiAlarms; MODELDATA_EXTRA_217 @@ -719,7 +732,7 @@ int8_t timezone:5; uint8_t adjustRTC:1; uint8_t inactivityTimer; - uint8_t mavbaud:3; + uint8_t telemetryBaudrate:3; int8_t splashMode:3; int8_t hapticMode:2; // -2=quiet, -1=only alarms, 0=no keys, 1=all int8_t switchesDelay; @@ -745,7 +758,7 @@ uint16_t mAhUsed; uint32_t globalTimer; int8_t temperatureCalib; - uint8_t btBaudrate; + uint8_t bluetoothBaudrate; uint8_t optrexDisplay; uint8_t sticksGain; uint8_t rotarySteps; @@ -816,7 +829,7 @@ settings.vBatMax = settings_v217.vBatMax; settings.backlightBright = settings_v217.backlightBright; settings.globalTimer = settings_v217.globalTimer; - settings.btBaudrate = settings_v217.btBaudrate; + settings.bluetoothBaudrate = settings_v217.bluetoothBaudrate; settings.countryCode = settings_v217.countryCode; settings.imperial = settings_v217.imperial; settings.ttsLanguage[0] = settings_v217.ttsLanguage[0]; @@ -842,7 +855,6 @@ #endif #if defined(PCBX9E) - settings.bluetoothEnable = settings_v217.bluetoothEnable; memcpy(settings.bluetoothName, settings_v217.bluetoothName, sizeof(settings.bluetoothName)); #endif @@ -1007,7 +1019,7 @@ newModel.switchWarningEnable = oldModel.switchWarningEnable; memcpy(newModel.gvars, oldModel.gvars, sizeof(newModel.gvars)); - memcpy(&newModel.frsky.rssiAlarms, &oldModel.frsky.rssiAlarms, sizeof(newModel.frsky.rssiAlarms)); + memcpy(&newModel.rssiAlarms, &oldModel.frsky.rssiAlarms, sizeof(newModel.rssiAlarms)); for (int i=0; i> (2*i)) & 0x03) == TELEMETRY_SCREEN_TYPE_VALUES) { diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/storage/sdcard_raw.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/storage/sdcard_raw.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/storage/sdcard_raw.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/storage/sdcard_raw.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -32,7 +32,7 @@ TRACE("writeFile(%s)", filename); FIL file; - char buf[8]; + unsigned char buf[8]; UINT written; FRESULT result = f_open(&file, filename, FA_CREATE_ALWAYS | FA_WRITE); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/storage/storage_common.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/storage/storage_common.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/storage/storage_common.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/storage/storage_common.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -55,9 +55,20 @@ pauseMixerCalculations(); } +#if defined(PCBTARANIS) || defined(PCBHORUS) +static void fixUpModel() +{ + // Ensure that when rfProtocol is RF_PROTO_OFF the type of the module is MODULE_TYPE_NONE + if (g_model.moduleData[INTERNAL_MODULE].type == MODULE_TYPE_XJT && g_model.moduleData[INTERNAL_MODULE].rfProtocol == RF_PROTO_OFF) + g_model.moduleData[INTERNAL_MODULE].type = MODULE_TYPE_NONE; +} +#endif void postModelLoad(bool alarms) { +#if defined(PCBTARANIS) || defined(PCBHORUS) + fixUpModel(); +#endif AUDIO_FLUSH(); flightReset(false); @@ -65,11 +76,13 @@ #if defined(GUI) if (alarms) { checkAll(); + PLAY_MODEL_NAME(); } #endif resumePulses(); } + customFunctionsReset(); restoreTimers(); @@ -104,7 +117,6 @@ LOAD_MODEL_BITMAP(); LUA_LOAD_MODEL_SCRIPTS(); SEND_FAILSAFE_1S(); - PLAY_MODEL_NAME(); } void storageFlushCurrentModel() diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/strhelpers.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/strhelpers.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/strhelpers.cpp 2017-05-31 19:49:19.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/strhelpers.cpp 2017-11-11 11:29:14.000000000 +0000 @@ -49,7 +49,7 @@ { if (c == '_') return 37; #if LEN_SPECIAL_CHARS > 0 - if (c < 0 && c+128 <= LEN_SPECIAL_CHARS) return 41 + (c+128); + if ((int8_t)c < 0 && c+128 <= LEN_SPECIAL_CHARS) return 41 + (c+128); #endif if (c >= 'a') return 'a' - c - 1; if (c >= 'A') return c - 'A' + 1; @@ -379,9 +379,18 @@ else if (idx <= MIXSRC_LAST_GVAR) { strAppendStringWithIndex(dest, STR_GV, idx - MIXSRC_GVAR1 + 1); } - else if (idx < MIXSRC_FIRST_TELEM) { + else if (idx < MIXSRC_FIRST_TIMER) { getStringAtIndex(dest, STR_VSRCRAW, idx-MIXSRC_Rud+1-MAX_LOGICAL_SWITCHES-MAX_TRAINER_CHANNELS-MAX_OUTPUT_CHANNELS-MAX_GVARS); } + else if (idx <= MIXSRC_LAST_TIMER) { + if(ZEXIST(g_model.timers[idx-MIXSRC_FIRST_TIMER].name)) { + zchar2str(dest,g_model.timers[idx-MIXSRC_FIRST_TIMER].name, LEN_TIMER_NAME); + dest[LEN_TIMER_NAME] = '\0'; + } + else { + getStringAtIndex(dest, STR_VSRCRAW, idx-MIXSRC_Rud+1-MAX_LOGICAL_SWITCHES-MAX_TRAINER_CHANNELS-MAX_OUTPUT_CHANNELS-MAX_GVARS); + } + } else { idx -= MIXSRC_FIRST_TELEM; div_t qr = div(idx, 3); @@ -400,7 +409,7 @@ if (digits == 0) { unsigned int tmp = value; digits = 1; - while (tmp >= 10) { + while (tmp >= radix) { ++digits; tmp /= radix; } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/common/arm/CMakeLists.txt opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/common/arm/CMakeLists.txt --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/common/arm/CMakeLists.txt 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/common/arm/CMakeLists.txt 2017-10-31 16:16:43.000000000 +0000 @@ -132,4 +132,5 @@ ppm_arm.cpp pxx_arm.cpp dsm2_arm.cpp - ) + sbus_arm.cpp + ) \ No newline at end of file diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/common/arm/stm32/adc_driver.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/common/arm/stm32/adc_driver.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/common/arm/stm32/adc_driver.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/common/arm/stm32/adc_driver.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -23,7 +23,7 @@ #if defined(SIMU) // not needed #elif defined(PCBX10) - const int8_t ana_direction[NUM_ANALOGS] = {1,-1,1,-1, -1,-1,-1, -1,1,1,1, -1}; + const int8_t ana_direction[NUM_ANALOGS] = {1,-1,1,-1, -1,1,-1, 1,-1, 1, 1,1}; #elif defined(PCBX9E) #if defined(HORUS_STICKS) const int8_t ana_direction[NUM_ANALOGS] = {1,-1,1,-1, -1,-1,-1,1, -1,1,1,1, -1}; @@ -44,11 +44,16 @@ const int8_t ana_direction[NUM_ANALOGS] = {1,-1,1,-1, -1,1,0, -1,1, 1}; #endif -#if defined(PCBX9E) - #define NUM_ANALOGS_ADC 10 - #define NUM_ANALOGS_ADC_EXT (NUM_ANALOGS - 10) +#if NUM_PWMANALOGS > 0 + #define FIRST_ANALOG_ADC (ANALOGS_PWM_ENABLED() ? NUM_PWMANALOGS : 0) + #define NUM_ANALOGS_ADC (ANALOGS_PWM_ENABLED() ? (NUM_ANALOGS - NUM_PWMANALOGS) : NUM_ANALOGS) +#elif defined(PCBX9E) + #define FIRST_ANALOG_ADC 0 + #define NUM_ANALOGS_ADC 10 + #define NUM_ANALOGS_ADC_EXT (NUM_ANALOGS - 10) #else - #define NUM_ANALOGS_ADC NUM_ANALOGS + #define FIRST_ANALOG_ADC 0 + #define NUM_ANALOGS_ADC NUM_ANALOGS #endif uint16_t adcValues[NUM_ANALOGS] __DMA; @@ -86,8 +91,14 @@ ADC_MAIN->SQR1 = (NUM_ANALOGS_ADC-1) << 20; // bits 23:20 = number of conversions #if defined(PCBX10) - ADC_MAIN->SQR2 = (ADC_CHANNEL_POT3<<0) + (ADC_CHANNEL_SLIDER1<<5) + (ADC_CHANNEL_SLIDER2<<10) + (ADC_CHANNEL_BATT<<15) + (ADC_CHANNEL_EXT1<<20) + (ADC_CHANNEL_EXT2<<25); // conversions 7 and more - ADC_MAIN->SQR3 = (ADC_CHANNEL_STICK_LH<<0) + (ADC_CHANNEL_STICK_LV<<5) + (ADC_CHANNEL_STICK_RV<<10) + (ADC_CHANNEL_STICK_RH<<15) + (ADC_CHANNEL_POT1<<20) + (ADC_CHANNEL_POT2<<25); // conversions 1 to 6 + if (ANALOGS_PWM_ENABLED()) { + ADC_MAIN->SQR2 = (ADC_CHANNEL_EXT1<<0) + (ADC_CHANNEL_EXT2<<5); // conversions 7 and more + ADC_MAIN->SQR3 = (ADC_CHANNEL_POT1<<0) + (ADC_CHANNEL_POT2<<5) + (ADC_CHANNEL_POT3<<10) + (ADC_CHANNEL_SLIDER1<<15) + (ADC_CHANNEL_SLIDER2<<20) + (ADC_CHANNEL_BATT<<25); // conversions 1 to 6 + } + else { + ADC_MAIN->SQR2 = (ADC_CHANNEL_POT3<<0) + (ADC_CHANNEL_SLIDER1<<5) + (ADC_CHANNEL_SLIDER2<<10) + (ADC_CHANNEL_BATT<<15) + (ADC_CHANNEL_EXT1<<20) + (ADC_CHANNEL_EXT2<<25); // conversions 7 and more + ADC_MAIN->SQR3 = (ADC_CHANNEL_STICK_LH<<0) + (ADC_CHANNEL_STICK_LV<<5) + (ADC_CHANNEL_STICK_RV<<10) + (ADC_CHANNEL_STICK_RH<<15) + (ADC_CHANNEL_POT1<<20) + (ADC_CHANNEL_POT2<<25); // conversions 1 to 6 + } #elif defined(PCBX9E) ADC_MAIN->SQR2 = (ADC_CHANNEL_POT4<<0) + (ADC_CHANNEL_SLIDER3<<5) + (ADC_CHANNEL_SLIDER4<<10) + (ADC_CHANNEL_BATT<<15); // conversions 7 and more ADC_MAIN->SQR3 = (ADC_CHANNEL_STICK_LH<<0) + (ADC_CHANNEL_STICK_LV<<5) + (ADC_CHANNEL_STICK_RV<<10) + (ADC_CHANNEL_STICK_RH<<15) + (ADC_CHANNEL_POT2<<20) + (ADC_CHANNEL_POT3<<25); // conversions 1 to 6 @@ -106,7 +117,7 @@ ADC_DMA_Stream->CR = DMA_SxCR_PL | ADC_DMA_SxCR_CHSEL | DMA_SxCR_MSIZE_0 | DMA_SxCR_PSIZE_0 | DMA_SxCR_MINC; ADC_DMA_Stream->PAR = CONVERT_PTR_UINT(&ADC_MAIN->DR); - ADC_DMA_Stream->M0AR = CONVERT_PTR_UINT(adcValues); + ADC_DMA_Stream->M0AR = CONVERT_PTR_UINT(&adcValues[FIRST_ANALOG_ADC]); ADC_DMA_Stream->NDTR = NUM_ANALOGS_ADC; ADC_DMA_Stream->FCR = DMA_SxFCR_DMDIS | DMA_SxFCR_FTH_0; @@ -125,6 +136,12 @@ ADC_EXT_DMA_Stream->NDTR = NUM_ANALOGS_ADC_EXT; ADC_EXT_DMA_Stream->FCR = DMA_SxFCR_DMDIS | DMA_SxFCR_FTH_0; #endif + +#if NUM_PWMANALOGS > 0 + if (ANALOGS_PWM_ENABLED()) { + pwmInit(); + } +#endif } void adcSingleRead() @@ -167,7 +184,7 @@ for (int i=0; i<4; i++) { adcSingleRead(); - for (uint8_t x=0; x> 2; } + +#if NUM_PWMANALOGS > 0 + if (ANALOGS_PWM_ENABLED()) { + pwmRead(adcValues); + } +#endif } // TODO diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/common/arm/stm32/bluetooth_driver.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/common/arm/stm32/bluetooth_driver.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/common/arm/stm32/bluetooth_driver.cpp 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/common/arm/stm32/bluetooth_driver.cpp 2017-11-20 18:44:06.000000000 +0000 @@ -0,0 +1,158 @@ +/* + * Copyright (C) OpenTX + * + * Based on code named + * th9x - http://code.google.com/p/th9x + * er9x - http://code.google.com/p/er9x + * gruvin9x - http://code.google.com/p/gruvin9x + * + * License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + * + * 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. + */ + +#include "opentx.h" + +Fifo btTxFifo; +Fifo btRxFifo; + +#if defined(PCBX7) +uint8_t btChipPresent = 0; +#endif + +enum BluetoothWriteState +{ + BLUETOOTH_WRITE_IDLE, + BLUETOOTH_WRITE_INIT, + BLUETOOTH_WRITING, + BLUETOOTH_WRITE_DONE +}; + +volatile uint8_t bluetoothWriteState = BLUETOOTH_WRITE_IDLE; + +void bluetoothInit(uint32_t baudrate) +{ + GPIO_InitTypeDef GPIO_InitStructure; + USART_InitTypeDef USART_InitStructure; + + USART_DeInit(BT_USART); + + GPIO_InitStructure.GPIO_Pin = BT_EN_GPIO_PIN; + GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT; + GPIO_InitStructure.GPIO_OType = GPIO_OType_PP; + GPIO_InitStructure.GPIO_Speed = GPIO_Speed_2MHz; + GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_NOPULL; + GPIO_Init(BT_EN_GPIO, &GPIO_InitStructure); + +#if defined(BT_BRTS_GPIO_PIN) + GPIO_InitStructure.GPIO_Pin = BT_BRTS_GPIO_PIN; + GPIO_Init(BT_BRTS_GPIO, &GPIO_InitStructure); + GPIO_SetBits(BT_BRTS_GPIO, BT_BRTS_GPIO_PIN); +#endif + +#if defined(BT_BCTS_GPIO_PIN) + GPIO_InitStructure.GPIO_Pin = BT_BCTS_GPIO_PIN; + GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN; + GPIO_Init(BT_BCTS_GPIO, &GPIO_InitStructure); +#endif + + GPIO_InitStructure.GPIO_Pin = BT_TX_GPIO_PIN|BT_RX_GPIO_PIN; + GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF; + GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP; + GPIO_Init(BT_GPIO_TXRX, &GPIO_InitStructure); + + GPIO_PinAFConfig(BT_GPIO_TXRX, BT_TX_GPIO_PinSource, BT_GPIO_AF); + GPIO_PinAFConfig(BT_GPIO_TXRX, BT_RX_GPIO_PinSource, BT_GPIO_AF); + + USART_DeInit(BT_USART); + USART_InitStructure.USART_BaudRate = baudrate; + USART_InitStructure.USART_Parity = USART_Parity_No; + USART_InitStructure.USART_StopBits = USART_StopBits_1; + USART_InitStructure.USART_WordLength = USART_WordLength_8b; + USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None; + USART_InitStructure.USART_Mode = USART_Mode_Rx | USART_Mode_Tx; + USART_Init(BT_USART, &USART_InitStructure); + + USART_Cmd(BT_USART, ENABLE); + USART_ITConfig(BT_USART, USART_IT_RXNE, ENABLE); + + NVIC_InitTypeDef NVIC_InitStructure; + NVIC_InitStructure.NVIC_IRQChannel = BT_USART_IRQn; + NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 8; + NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0; + NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; + NVIC_Init(&NVIC_InitStructure); + + btRxFifo.clear(); + btTxFifo.clear(); + bluetoothWriteState = BLUETOOTH_WRITE_IDLE; + + GPIO_ResetBits(BT_EN_GPIO, BT_EN_GPIO_PIN); // open bluetooth +} + +void bluetoothDone() +{ + GPIO_SetBits(BT_EN_GPIO, BT_EN_GPIO_PIN); // close bluetooth +} + +extern "C" void BT_USART_IRQHandler(void) +{ + DEBUG_INTERRUPT(INT_BLUETOOTH); + if (USART_GetITStatus(BT_USART, USART_IT_RXNE) != RESET) { + USART_ClearITPendingBit(BT_USART, USART_IT_RXNE); + uint8_t byte = USART_ReceiveData(BT_USART); + btRxFifo.push(byte); +#if defined(PCBX7) + if (!btChipPresent) { //This is to differentiate X7 and X7S + btChipPresent = 1; + bluetoothDone(); + } +#endif + } + + if (USART_GetITStatus(BT_USART, USART_IT_TXE) != RESET) { + uint8_t byte; + bool result = btTxFifo.pop(byte); + if (result) { + USART_SendData(BT_USART, byte); + } + else { + USART_ITConfig(BT_USART, USART_IT_TXE, DISABLE); + bluetoothWriteState = BLUETOOTH_WRITE_DONE; + } + } +} + +void bluetoothWriteWakeup(void) +{ + if (bluetoothWriteState == BLUETOOTH_WRITE_IDLE) { + if (!btTxFifo.isEmpty()) { + bluetoothWriteState = BLUETOOTH_WRITE_INIT; +#if defined(BT_BRTS_GPIO_PIN) + GPIO_ResetBits(BT_BRTS_GPIO, BT_BRTS_GPIO_PIN); +#endif + } + } + else if (bluetoothWriteState == BLUETOOTH_WRITE_INIT) { + bluetoothWriteState = BLUETOOTH_WRITING; + USART_ITConfig(BT_USART, USART_IT_TXE, ENABLE); + } + else if (bluetoothWriteState == BLUETOOTH_WRITE_DONE) { + bluetoothWriteState = BLUETOOTH_WRITE_IDLE; +#if defined(BT_BRTS_GPIO_PIN) + GPIO_SetBits(BT_BRTS_GPIO, BT_BRTS_GPIO_PIN); +#endif + } +} + +uint8_t bluetoothIsWriting(void) +{ + return bluetoothWriteState != BLUETOOTH_WRITE_IDLE; +} diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/common/arm/stm32/CMakeLists.txt opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/common/arm/stm32/CMakeLists.txt --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/common/arm/stm32/CMakeLists.txt 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/common/arm/stm32/CMakeLists.txt 2017-12-17 16:22:27.000000000 +0000 @@ -1,9 +1,8 @@ set(LUA "NO" CACHE STRING "Lua scripts (YES/NO/NO_MODEL_SCRIPTS)") set_property(CACHE LUA PROPERTY STRINGS YES NO NO_MODEL_SCRIPTS) set(LUA_SCRIPT_LOAD_MODE "" CACHE STRING "Script loading mode and compilation flags [btTxcd] (see loadScript() API docs). Blank for default ('bt' on radio, 'T' on SIMU/DEBUG builds)") -set(USB "JOYSTICK" CACHE STRING "USB option (JOYSTICK/MASSSTORAGE/SERIAL)") -set_property(CACHE USB PROPERTY STRINGS JOYSTICK MASSSTORAGE SERIAL) option(LUA_COMPILER "Pre-compile and save Lua scripts" OFF) +option(LUA_ALLOCATOR_TRACER "Trace Lua memory (de)allocations to debug port (also needs DEBUG=YES NANO=NO)" OFF) set(ARCH ARM) set(STM32USB_DIR ${THIRDPARTY_DIR}/STM32_USB-Host-Device_Lib_V2.2.0/Libraries) @@ -38,36 +37,29 @@ ../common/arm/stm32/usbd_usr.cpp ../common/arm/stm32/usb_driver.cpp ) -if(USB STREQUAL SERIAL) - add_definitions(-DUSB_SERIAL) - set(FIRMWARE_TARGET_SRC - ${FIRMWARE_TARGET_SRC} - ../common/arm/stm32/usbd_cdc.cpp - ) - set(STM32USB_SRC - ${STM32USB_SRC} - STM32_USB_Device_Library/Class/cdc/src/usbd_cdc_core.c - ) -elseif(USB STREQUAL MASSSTORAGE) - add_definitions(-DUSB_MASS_STORAGE) - set(STM32USB_SRC - ${STM32USB_SRC} - STM32_USB_Device_Library/Class/msc/src/usbd_msc_data.c - STM32_USB_Device_Library/Class/msc/src/usbd_msc_scsi.c - STM32_USB_Device_Library/Class/msc/src/usbd_msc_bot.c - STM32_USB_Device_Library/Class/msc/src/usbd_msc_core.c - ) - set(FIRMWARE_TARGET_SRC - ${FIRMWARE_TARGET_SRC} - ../common/arm/stm32/usbd_storage_msd.cpp - ) -else() - add_definitions(-DUSB_JOYSTICK) - set(FIRMWARE_TARGET_SRC - ${FIRMWARE_TARGET_SRC} - ../common/arm/stm32/usbd_hid_joystick.c - ) -endif() +set(FIRMWARE_TARGET_SRC + ${FIRMWARE_TARGET_SRC} + ../common/arm/stm32/usbd_cdc.cpp + ) +set(STM32USB_SRC + ${STM32USB_SRC} + STM32_USB_Device_Library/Class/cdc/src/usbd_cdc_core.c + ) +set(STM32USB_SRC + ${STM32USB_SRC} + STM32_USB_Device_Library/Class/msc/src/usbd_msc_data.c + STM32_USB_Device_Library/Class/msc/src/usbd_msc_scsi.c + STM32_USB_Device_Library/Class/msc/src/usbd_msc_bot.c + STM32_USB_Device_Library/Class/msc/src/usbd_msc_core.c + ) +set(FIRMWARE_TARGET_SRC + ${FIRMWARE_TARGET_SRC} + ../common/arm/stm32/usbd_storage_msd.cpp + ) +set(FIRMWARE_TARGET_SRC + ${FIRMWARE_TARGET_SRC} + ../common/arm/stm32/usbd_hid_joystick.c + ) if(GVARS) set(GUI_SRC ${GUI_SRC} diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/common/arm/stm32/rtc_driver.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/common/arm/stm32/rtc_driver.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/common/arm/stm32/rtc_driver.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/common/arm/stm32/rtc_driver.cpp 2017-11-10 17:23:25.000000000 +0000 @@ -64,7 +64,15 @@ RCC_APB1PeriphClockCmd(RCC_APB1Periph_PWR, ENABLE); PWR_BackupAccessCmd(ENABLE); RCC_LSEConfig(RCC_LSE_ON); - while(RCC_GetFlagStatus(RCC_FLAG_LSERDY) == RESET); + + // Prevent lockup in case of 32kHz oscillator failure + uint32_t i = 0; + while(RCC_GetFlagStatus(RCC_FLAG_LSERDY) == RESET) + { + if ( ++i > 1000000 ) + return; + } + RCC_RTCCLKConfig(RCC_RTCCLKSource_LSE); RCC_RTCCLKCmd(ENABLE); RTC_WaitForSynchro(); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/common/arm/stm32/serial2_driver.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/common/arm/stm32/serial2_driver.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/common/arm/stm32/serial2_driver.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/common/arm/stm32/serial2_driver.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -91,7 +91,7 @@ case UART_MODE_TELEMETRY_MIRROR: uart3Setup(FRSKY_SPORT_BAUDRATE, false); break; -#if !defined(USB_SERIAL) && (defined(DEBUG) || defined(CLI)) +#if defined(DEBUG) || defined(CLI) case UART_MODE_DEBUG: uart3Setup(DEBUG_BAUDRATE, false); break; @@ -153,19 +153,21 @@ } } -#if !defined(USB_SERIAL) && defined(CLI) - // Receive - uint32_t status = SERIAL_USART->SR; - while (status & (USART_FLAG_RXNE | USART_FLAG_ERRORS)) { - uint8_t data = SERIAL_USART->DR; - if (!(status & USART_FLAG_ERRORS)) { - switch (serial2Mode) { - case UART_MODE_DEBUG: - cliRxFifo.push(data); - break; +#if defined(CLI) + if (!(getSelectedUsbMode() == USB_SERIAL_MODE)) { + // Receive + uint32_t status = SERIAL_USART->SR; + while (status & (USART_FLAG_RXNE | USART_FLAG_ERRORS)) { + uint8_t data = SERIAL_USART->DR; + if (!(status & USART_FLAG_ERRORS)) { + switch (serial2Mode) { + case UART_MODE_DEBUG: + cliRxFifo.push(data); + break; + } } + status = SERIAL_USART->SR; } - status = SERIAL_USART->SR; } #endif } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/common/arm/stm32/usbd_conf.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/common/arm/stm32/usbd_conf.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/common/arm/stm32/usbd_conf.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/common/arm/stm32/usbd_conf.h 2017-10-31 16:16:43.000000000 +0000 @@ -2,7 +2,7 @@ * Copyright (C) OpenTX * * Based on code named - * th9x - http://code.google.com/p/th9x + * th9x - http://code.google.com/p/th9x * er9x - http://code.google.com/p/er9x * gruvin9x - http://code.google.com/p/gruvin9x * @@ -27,7 +27,7 @@ #define USBD_CFG_MAX_NUM 1 #define USBD_ITF_MAX_NUM 1 -#define USB_MAX_STR_DESC_SIZ 64 +#define USB_MAX_STR_DESC_SIZ 64 #define USBD_SELF_POWERED @@ -61,4 +61,3 @@ /************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/ - diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/common/arm/stm32/usbd_desc.c opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/common/arm/stm32/usbd_desc.c --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/common/arm/stm32/usbd_desc.c 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/common/arm/stm32/usbd_desc.c 2017-10-31 16:16:43.000000000 +0000 @@ -2,7 +2,7 @@ * Copyright (C) OpenTX * * Based on code named - * th9x - http://code.google.com/p/th9x + * th9x - http://code.google.com/p/th9x * er9x - http://code.google.com/p/er9x * gruvin9x - http://code.google.com/p/gruvin9x * @@ -29,27 +29,30 @@ #include "usbd_req.h" #include "usb_regs.h" + +#include "usb_driver.h" + /** @addtogroup STM32_USB_OTG_DEVICE_LIBRARY * @{ */ -/** @defgroup USBD_DESC +/** @defgroup USBD_DESC * @brief USBD descriptors module * @{ - */ + */ /** @defgroup USBD_DESC_Private_TypesDefinitions * @{ - */ + */ /** * @} - */ + */ /** @defgroup USBD_DESC_Private_Defines * @{ - */ + */ #define USBD_VID 0x0483 @@ -59,31 +62,29 @@ #if defined(BOOT) - #define USBD_PID 0x5720 - #define USBD_PRODUCT_FS_STRING USB_NAME " Bootloader" - #define USBD_CONFIGURATION_FS_STRING "MSC Config" - #define USBD_INTERFACE_FS_STRING "MSC Interface" -#elif defined(USB_JOYSTICK) - #define USBD_PID 0x5710 - #define USBD_PRODUCT_FS_STRING USB_NAME " Joystick" - #define USBD_CONFIGURATION_FS_STRING "HID Config" - #define USBD_INTERFACE_FS_STRING "HID Interface" -#elif defined(USB_SERIAL) - #define USBD_PID 0x5740 // do not change, this ID is used by the ST USB driver for Windows - #define USBD_PRODUCT_FS_STRING USB_NAME " Serial Port" - #define USBD_CONFIGURATION_FS_STRING "VSP Config" - #define USBD_INTERFACE_FS_STRING "VSP Interface" -#elif defined(USB_MASS_STORAGE) - #define USBD_PID 0x5720 - #define USBD_PRODUCT_FS_STRING USB_NAME " Mass Storage" - #define USBD_CONFIGURATION_FS_STRING "MSC Config" - #define USBD_INTERFACE_FS_STRING "MSC Interface" + #define USBD_MSC_PRODUCT_FS_STRING USB_NAME " Bootloader" +#else + #define USBD_MSC_PRODUCT_FS_STRING USB_NAME " Mass Storage" #endif +#define USBD_MSC_PID 0x5720 +#define USBD_MSC_CONFIGURATION_FS_STRING "MSC Config" +#define USBD_MSC_INTERFACE_FS_STRING "MSC Interface" + +#define USBD_HID_PID 0x5710 +#define USBD_HID_PRODUCT_FS_STRING USB_NAME " Joystick" +#define USBD_HID_CONFIGURATION_FS_STRING "HID Config" +#define USBD_HID_INTERFACE_FS_STRING "HID Interface" + +#define USBD_CDC_PID 0x5740 // do not change, this ID is used by the ST USB driver for Windows +#define USBD_CDC_PRODUCT_FS_STRING USB_NAME " Serial Port" +#define USBD_CDC_CONFIGURATION_FS_STRING "VSP Config" +#define USBD_CDC_INTERFACE_FS_STRING "VSP Interface" + const USBD_DEVICE USR_desc = { USBD_USR_DeviceDescriptor, - USBD_USR_LangIDStrDescriptor, + USBD_USR_LangIDStrDescriptor, USBD_USR_ManufacturerStrDescriptor, USBD_USR_ProductStrDescriptor, USBD_USR_SerialStrDescriptor, @@ -91,28 +92,6 @@ USBD_USR_InterfaceStrDescriptor, }; -/* USB Standard Device Descriptor */ -__ALIGN_BEGIN const uint8_t USBD_DeviceDesc[USB_SIZ_DEVICE_DESC] __ALIGN_END = -{ - USB_SIZ_DEVICE_DESC, /*bLength */ - USB_DEVICE_DESCRIPTOR_TYPE, /*bDescriptorType*/ - 0x00, /*bcdUSB */ - 0x02, - 0x00, /*bDeviceClass*/ - 0x00, /*bDeviceSubClass*/ - 0x00, /*bDeviceProtocol*/ - USB_OTG_MAX_EP0_SIZE, /*bMaxPacketSize*/ - LOBYTE(USBD_VID), /*idVendor*/ - HIBYTE(USBD_VID), /*idVendor*/ - LOBYTE(USBD_PID), /*idVendor*/ - HIBYTE(USBD_PID), /*idVendor*/ - 0x00, /*bcdDevice rel. 2.00*/ - 0x02, - USBD_IDX_MFC_STR, /*Index of manufacturer string*/ - USBD_IDX_PRODUCT_STR, /*Index of product string*/ - USBD_IDX_SERIAL_STR, /*Index of serial number string*/ - USBD_CFG_MAX_NUM /*bNumConfigurations*/ -}; /* USB_DeviceDescriptor */ /* USB Standard Device Descriptor */ __ALIGN_BEGIN const uint8_t USBD_DeviceQualifierDesc[USB_LEN_DEV_QUALIFIER_DESC] __ALIGN_END = @@ -132,16 +111,16 @@ /* USB Standard Device Descriptor */ __ALIGN_BEGIN const uint8_t USBD_LangIDDesc[USB_SIZ_STRING_LANGID] __ALIGN_END = { - USB_SIZ_STRING_LANGID, - USB_DESC_TYPE_STRING, + USB_SIZ_STRING_LANGID, + USB_DESC_TYPE_STRING, LOBYTE(USBD_LANGID_STRING), - HIBYTE(USBD_LANGID_STRING), + HIBYTE(USBD_LANGID_STRING), }; __ALIGN_BEGIN uint8_t USBD_StrDesc[USB_MAX_STR_DESC_SIZ] __ALIGN_END ; // modified by OpenTX /* -* @brief USBD_USR_DeviceDescriptor +* @brief USBD_USR_DeviceDescriptor * return the device descriptor * @param speed : current device speed * @param length : pointer to data length variable @@ -149,13 +128,50 @@ */ uint8_t * USBD_USR_DeviceDescriptor( uint8_t speed , uint16_t *length) { + int pid=0; + + switch (getSelectedUsbMode()) { + case USB_JOYSTICK_MODE: + pid = USBD_HID_PID; + break; + case USB_SERIAL_MODE: + pid = USBD_CDC_PID; + break; + case USB_MASS_STORAGE_MODE: + pid = USBD_MSC_PID; + break; + } + + /* USB Standard Device Descriptor */ + __ALIGN_BEGIN const uint8_t USBD_DeviceDesc[USB_SIZ_DEVICE_DESC] __ALIGN_END = + { + USB_SIZ_DEVICE_DESC, /*bLength */ + USB_DEVICE_DESCRIPTOR_TYPE, /*bDescriptorType*/ + 0x00, /*bcdUSB */ + 0x02, + 0x00, /*bDeviceClass*/ + 0x00, /*bDeviceSubClass*/ + 0x00, /*bDeviceProtocol*/ + USB_OTG_MAX_EP0_SIZE, /*bMaxPacketSize*/ + LOBYTE(USBD_VID), /*idVendor*/ + HIBYTE(USBD_VID), /*idVendor*/ + LOBYTE(pid), /*idVendor*/ + HIBYTE(pid), /*idVendor*/ + 0x00, /*bcdDevice rel. 2.00*/ + 0x02, + USBD_IDX_MFC_STR, /*Index of manufacturer string*/ + USBD_IDX_PRODUCT_STR, /*Index of product string*/ + USBD_IDX_SERIAL_STR, /*Index of serial number string*/ + USBD_CFG_MAX_NUM /*bNumConfigurations*/ + }; /* USB_DeviceDescriptor */ + *length = sizeof(USBD_DeviceDesc); memcpy(USBD_StrDesc, USBD_DeviceDesc, *length); return USBD_StrDesc; } /** -* @brief USBD_USR_LangIDStrDescriptor +* @brief USBD_USR_LangIDStrDescriptor * return the LangID string descriptor * @param speed : current device speed * @param length : pointer to data length variable @@ -163,14 +179,14 @@ */ uint8_t * USBD_USR_LangIDStrDescriptor( uint8_t speed , uint16_t *length) { - *length = sizeof(USBD_LangIDDesc); + *length = sizeof(USBD_LangIDDesc); memcpy(USBD_StrDesc, USBD_LangIDDesc, *length); return USBD_StrDesc; } /** -* @brief USBD_USR_ProductStrDescriptor +* @brief USBD_USR_ProductStrDescriptor * return the product string descriptor * @param speed : current device speed * @param length : pointer to data length variable @@ -178,12 +194,23 @@ */ uint8_t * USBD_USR_ProductStrDescriptor( uint8_t speed , uint16_t *length) { - USBD_GetString ((uint8_t*)USBD_PRODUCT_FS_STRING, USBD_StrDesc, length); + switch (getSelectedUsbMode()) { + case USB_JOYSTICK_MODE: + USBD_GetString ((uint8_t*)USBD_HID_PRODUCT_FS_STRING, USBD_StrDesc, length); + break; + case USB_SERIAL_MODE: + USBD_GetString ((uint8_t*)USBD_CDC_PRODUCT_FS_STRING, USBD_StrDesc, length); + break; + case USB_MASS_STORAGE_MODE: + USBD_GetString ((uint8_t*)USBD_MSC_PRODUCT_FS_STRING, USBD_StrDesc, length); + break; + } + return USBD_StrDesc; } /** -* @brief USBD_USR_ManufacturerStrDescriptor +* @brief USBD_USR_ManufacturerStrDescriptor * return the manufacturer string descriptor * @param speed : current device speed * @param length : pointer to data length variable @@ -196,7 +223,7 @@ } /** -* @brief USBD_USR_SerialStrDescriptor +* @brief USBD_USR_SerialStrDescriptor * return the serial number string descriptor * @param speed : current device speed * @param length : pointer to data length variable @@ -209,7 +236,7 @@ } /** -* @brief USBD_USR_ConfigStrDescriptor +* @brief USBD_USR_ConfigStrDescriptor * return the configuration string descriptor * @param speed : current device speed * @param length : pointer to data length variable @@ -217,13 +244,23 @@ */ uint8_t * USBD_USR_ConfigStrDescriptor( uint8_t speed , uint16_t *length) { - USBD_GetString ((uint8_t *)USBD_CONFIGURATION_FS_STRING, USBD_StrDesc, length); - return USBD_StrDesc; + switch (getSelectedUsbMode()) { + case USB_JOYSTICK_MODE: + USBD_GetString ((uint8_t*)USBD_HID_CONFIGURATION_FS_STRING, USBD_StrDesc, length); + break; + case USB_SERIAL_MODE: + USBD_GetString ((uint8_t*)USBD_CDC_CONFIGURATION_FS_STRING, USBD_StrDesc, length); + break; + case USB_MASS_STORAGE_MODE: + USBD_GetString ((uint8_t*)USBD_MSC_CONFIGURATION_FS_STRING, USBD_StrDesc, length); + break; + } + return USBD_StrDesc; } /** -* @brief USBD_USR_InterfaceStrDescriptor +* @brief USBD_USR_InterfaceStrDescriptor * return the interface string descriptor * @param speed : current device speed * @param length : pointer to data length variable @@ -231,9 +268,18 @@ */ uint8_t * USBD_USR_InterfaceStrDescriptor( uint8_t speed , uint16_t *length) { - USBD_GetString ((uint8_t*)USBD_INTERFACE_FS_STRING, USBD_StrDesc, length); - return USBD_StrDesc; + switch (getSelectedUsbMode()) { + case USB_JOYSTICK_MODE: + USBD_GetString ((uint8_t*)USBD_HID_INTERFACE_FS_STRING, USBD_StrDesc, length); + break; + case USB_SERIAL_MODE: + USBD_GetString ((uint8_t*)USBD_CDC_INTERFACE_FS_STRING, USBD_StrDesc, length); + break; + case USB_MASS_STORAGE_MODE: + USBD_GetString ((uint8_t*)USBD_MSC_INTERFACE_FS_STRING, USBD_StrDesc, length); + break; + } + return USBD_StrDesc; } /************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/ - diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/common/arm/stm32/usb_driver.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/common/arm/stm32/usb_driver.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/common/arm/stm32/usb_driver.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/common/arm/stm32/usb_driver.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -2,7 +2,7 @@ * Copyright (C) OpenTX * * Based on code named - * th9x - http://code.google.com/p/th9x + * th9x - http://code.google.com/p/th9x * er9x - http://code.google.com/p/er9x * gruvin9x - http://code.google.com/p/gruvin9x * @@ -31,6 +31,21 @@ #include "debug.h" static bool usbDriverStarted = false; +#if defined(BOOT) +static usbMode selectedUsbMode = USB_MASS_STORAGE_MODE; +#else +static usbMode selectedUsbMode = USB_UNSELECTED_MODE; +#endif + +int getSelectedUsbMode() +{ + return selectedUsbMode; +} + +void setSelectedUsbMode(int mode) +{ + selectedUsbMode = usbMode (mode); +} int usbPlugged() { @@ -70,16 +85,23 @@ void usbStart() { -#if defined(USB_JOYSTICK) - // initialize USB as HID device - USBD_Init(&USB_OTG_dev, USB_OTG_FS_CORE_ID, &USR_desc, &USBD_HID_cb, &USR_cb); -#elif defined(USB_SERIAL) - // initialize USB as CDC device (virtual serial port) - USBD_Init(&USB_OTG_dev, USB_OTG_FS_CORE_ID, &USR_desc, &USBD_CDC_cb, &USR_cb); -#elif defined(USB_MASS_STORAGE) - // initialize USB as MSC device - USBD_Init(&USB_OTG_dev, USB_OTG_FS_CORE_ID, &USR_desc, &USBD_MSC_cb, &USR_cb); + switch (getSelectedUsbMode()) { +#if !defined(BOOT) + case USB_JOYSTICK_MODE: + // initialize USB as HID device + USBD_Init(&USB_OTG_dev, USB_OTG_FS_CORE_ID, &USR_desc, &USBD_HID_cb, &USR_cb); + break; + case USB_SERIAL_MODE: + // initialize USB as CDC device (virtual serial port) + USBD_Init(&USB_OTG_dev, USB_OTG_FS_CORE_ID, &USR_desc, &USBD_CDC_cb, &USR_cb); + break; #endif + default: + case USB_MASS_STORAGE_MODE: + // initialize USB as MSC device + USBD_Init(&USB_OTG_dev, USB_OTG_FS_CORE_ID, &USR_desc, &USBD_MSC_cb, &USR_cb); + break; + } usbDriverStarted = true; } @@ -89,12 +111,12 @@ USBD_DeInit(&USB_OTG_dev); } -uint8_t usbStarted() +bool usbStarted() { return usbDriverStarted; } -#if defined(USB_JOYSTICK) +#if !defined(BOOT) /* Prepare and send new USB data packet @@ -135,5 +157,4 @@ USBD_HID_SendReport(&USB_OTG_dev, HID_Buffer, HID_IN_PACKET); } } - -#endif // #defined(USB_JOYSTICK) +#endif diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/common/arm/stm32/usb_driver.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/common/arm/stm32/usb_driver.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/common/arm/stm32/usb_driver.h 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/common/arm/stm32/usb_driver.h 2017-12-17 16:22:27.000000000 +0000 @@ -0,0 +1,55 @@ +/* + * Copyright (C) OpenTX + * + * Based on code named + * th9x - http://code.google.com/p/th9x + * er9x - http://code.google.com/p/er9x + * gruvin9x - http://code.google.com/p/gruvin9x + * + * License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + * + * 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. + */ + +#ifndef OPENTX_USB_DRIVER_H +#define OPENTX_USB_DRIVER_H + +// USB driver +enum usbMode { + USB_UNSELECTED_MODE, + USB_JOYSTICK_MODE, + USB_MASS_STORAGE_MODE, + USB_SERIAL_MODE, +#if defined(DEBUG) + USB_MAX_MODE=USB_SERIAL_MODE +#else + USB_MAX_MODE=USB_MASS_STORAGE_MODE +#endif +}; + +int usbPlugged(); +void usbInit(); +void usbStart(); +void usbStop(); +bool usbStarted(); +int getSelectedUsbMode(); +void setSelectedUsbMode(int mode); + +void usbSerialPutc(uint8_t c); + +// Used in view_statistics.cpp +#if defined(DEBUG) && !defined(BOOT) + extern uint16_t usbWraps; + extern uint16_t charsWritten; + extern volatile uint32_t APP_Rx_ptr_in; + extern volatile uint32_t APP_Rx_ptr_out; +#endif + +#endif diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/common/arm/stm32/usbd_storage_msd.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/common/arm/stm32/usbd_storage_msd.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/common/arm/stm32/usbd_storage_msd.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/common/arm/stm32/usbd_storage_msd.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -464,7 +464,11 @@ { { 'F', 'I', 'R', 'M', 'W', 'A', 'R', 'E'}, { 'B', 'I', 'N'}, - 0x20, // Archive +#if defined(BOOT) + 0x20, // Archive +#else + 0x21, // Readonly+Archive +#endif 0x00, 0x3E, 0xA301, @@ -739,6 +743,9 @@ } } else if (sector < 3 + (EEPROM_SIZE/BLOCK_SIZE) + (FLASHSIZE/BLOCK_SIZE)) { +#if !defined(BOOT) // Don't allow overwrite of running firmware + return -1; +#else // firmware uint32_t address; address = sector - 3 - (EEPROM_SIZE/BLOCK_SIZE); @@ -765,6 +772,7 @@ operation = FATWRITE_NONE; } } +#endif } return 0 ; } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/common/arm/stm32/usbd_usr.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/common/arm/stm32/usbd_usr.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/common/arm/stm32/usbd_usr.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/common/arm/stm32/usbd_usr.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -2,7 +2,7 @@ * Copyright (C) OpenTX * * Based on code named - * th9x - http://code.google.com/p/th9x + * th9x - http://code.google.com/p/th9x * er9x - http://code.google.com/p/er9x * gruvin9x - http://code.google.com/p/gruvin9x * @@ -35,9 +35,9 @@ USBD_USR_DeviceConfigured, USBD_USR_DeviceSuspended, USBD_USR_DeviceResumed, - + USBD_USR_DeviceConnected, - USBD_USR_DeviceDisconnected, + USBD_USR_DeviceDisconnected, }; } @@ -69,10 +69,10 @@ */ void USBD_USR_DeviceConfigured (void) { - + } /** -* @brief Displays the message on LCD on device suspend event +* @brief Displays the message on LCD on device suspend event * @param None * @retval None */ @@ -112,9 +112,10 @@ */ void USBD_USR_DeviceDisconnected (void) { -#if !defined(BOOT) && defined(USB_MASS_STORAGE) && defined(EEPROM) +#if !defined(BOOT) && defined(EEPROM) // TODO is it really needed if we didn't write the EEPROM? - NVIC_SystemReset(); +// if (getSelectedUsbMode() == USB_MASS_STORAGE_MODE) +// NVIC_SystemReset(); #endif } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/horus/backlight_driver.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/horus/backlight_driver.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/horus/backlight_driver.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/horus/backlight_driver.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -55,7 +55,7 @@ } #elif defined(PCBX10) BL_TIMER->ARR = 100; - BL_TIMER->PSC = BL_TIMER_FREQ / 10000 - 1; // 1kHz + BL_TIMER->PSC = BL_TIMER_FREQ / 1000000 - 1; // 10kHz (same as FrOS) BL_TIMER->CCMR2 = TIM_CCMR2_OC3M_1 | TIM_CCMR2_OC3M_2 | TIM_CCMR2_OC3PE; // PWM mode 1 BL_TIMER->CCER = TIM_CCER_CC3E | TIM_CCER_CC3NE; BL_TIMER->CCR3 = 100; @@ -67,18 +67,14 @@ void backlightEnable(uint8_t dutyCycle) { - if (dutyCycle < 5) { - dutyCycle = 5; - } - #if defined(PCBX12S) if (IS_HORUS_PROD()) { BL_TIMER->CCR4 = dutyCycle; } else { - BL_TIMER->CCR1 = (100 - dutyCycle); + BL_TIMER->CCR1 = BACKLIGHT_LEVEL_MAX - dutyCycle; } #elif defined(PCBX10) - BL_TIMER->CCR3 = (100 - dutyCycle); + BL_TIMER->CCR3 = BACKLIGHT_LEVEL_MAX - dutyCycle; #endif } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/horus/bluetooth_driver.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/horus/bluetooth_driver.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/horus/bluetooth_driver.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/horus/bluetooth_driver.cpp 1970-01-01 00:00:00.000000000 +0000 @@ -1,261 +0,0 @@ -/* - * Copyright (C) OpenTX - * - * Based on code named - * th9x - http://code.google.com/p/th9x - * er9x - http://code.google.com/p/er9x - * gruvin9x - http://code.google.com/p/gruvin9x - * - * License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License version 2 as - * published by the Free Software Foundation. - * - * 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. - */ - -#include "opentx.h" - -Fifo btTxFifo; -Fifo btRxFifo; - -enum BluetoothState -{ - BLUETOOTH_INIT, - BLUETOOTH_WAIT_TTM, - BLUETOOTH_WAIT_BAUDRATE_CHANGE, - BLUETOOTH_OK, -}; - -enum BluetoothWriteState -{ - BLUETOOTH_WRITE_IDLE, - BLUETOOTH_WRITE_INIT, - BLUETOOTH_WRITING, - BLUETOOTH_WRITE_DONE -}; - -volatile uint8_t bluetoothState = BLUETOOTH_INIT; -volatile uint8_t bluetoothWriteState = BLUETOOTH_WRITE_IDLE; - -void bluetoothInit(uint32_t baudrate) -{ - GPIO_InitTypeDef GPIO_InitStructure; - USART_InitTypeDef USART_InitStructure; - - USART_DeInit(BT_USART); - - RCC_AHB1PeriphClockCmd(BT_RCC_AHB1Periph, ENABLE); - RCC_APB2PeriphClockCmd(RCC_APB2Periph_USART6, ENABLE); - - GPIO_InitStructure.GPIO_Pin = BT_EN_GPIO_PIN; - GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT; - GPIO_InitStructure.GPIO_OType = GPIO_OType_PP; - GPIO_InitStructure.GPIO_Speed = GPIO_Speed_2MHz; - GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_NOPULL; - GPIO_Init(BT_EN_GPIO, &GPIO_InitStructure); - -#if defined(BT_BRTS_GPIO_PIN) - GPIO_InitStructure.GPIO_Pin = BT_BRTS_GPIO_PIN; - GPIO_Init(BT_BRTS_GPIO, &GPIO_InitStructure); - GPIO_SetBits(BT_BRTS_GPIO, BT_BRTS_GPIO_PIN); -#endif - -#if defined(BT_BCTS_GPIO_PIN) - GPIO_InitStructure.GPIO_Pin = BT_BCTS_GPIO_PIN; - GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN; - GPIO_Init(BT_BCTS_GPIO, &GPIO_InitStructure); -#endif - - GPIO_InitStructure.GPIO_Pin = BT_TX_GPIO_PIN|BT_RX_GPIO_PIN; - GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF; - GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP; - GPIO_Init(BT_GPIO_TXRX, &GPIO_InitStructure); - - GPIO_PinAFConfig(BT_GPIO_TXRX, BT_TX_GPIO_PinSource, BT_GPIO_AF); - GPIO_PinAFConfig(BT_GPIO_TXRX, BT_RX_GPIO_PinSource, BT_GPIO_AF); - - USART_DeInit(BT_USART); - USART_InitStructure.USART_BaudRate = baudrate; - USART_InitStructure.USART_Parity = USART_Parity_No; - USART_InitStructure.USART_StopBits = USART_StopBits_1; - USART_InitStructure.USART_WordLength = USART_WordLength_8b; - USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None; - USART_InitStructure.USART_Mode = USART_Mode_Rx | USART_Mode_Tx; - USART_Init(BT_USART, &USART_InitStructure); - - USART_Cmd(BT_USART, ENABLE); - USART_ITConfig(BT_USART, USART_IT_RXNE, ENABLE); - - NVIC_InitTypeDef NVIC_InitStructure; - NVIC_InitStructure.NVIC_IRQChannel = BT_USART_IRQn; - NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 8; - NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0; - NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; - NVIC_Init(&NVIC_InitStructure); - - GPIO_ResetBits(BT_EN_GPIO, BT_EN_GPIO_PIN); // open bluetooth -} - -void bluetoothDone() -{ - GPIO_SetBits(BT_EN_GPIO, BT_EN_GPIO_PIN); // close bluetooth -} - -extern "C" void USART6_IRQHandler(void) -{ - DEBUG_INTERRUPT(INT_BLUETOOTH); - if (USART_GetITStatus(BT_USART, USART_IT_RXNE) != RESET) { - USART_ClearITPendingBit(BT_USART, USART_IT_RXNE); - uint8_t byte = USART_ReceiveData(BT_USART); - btRxFifo.push(byte); - } - - if (USART_GetITStatus(BT_USART, USART_IT_TXE) != RESET) { - uint8_t byte; - bool result = btTxFifo.pop(byte); - if (result) { - USART_SendData(BT_USART, byte); - } - else { - USART_ITConfig(BT_USART, USART_IT_TXE, DISABLE); - bluetoothWriteState = BLUETOOTH_WRITE_DONE; - } - } -} - -void bluetoothWrite(const void * buffer, int len) -{ - uint8_t * data = (uint8_t *)buffer; - for (int i=0; i waitEnd) { - TRACE("bt rename"); - char ttm[] = "TTM:REN"; - int index = 0; - uint8_t c; - bool found = false; - while (btRxFifo.pop(c)) { - if (c == ttm[index]) { - index++; - if (index == sizeof(ttm)-1) { - found = true; - break; - } - } - else { - index = 0; - } - } - if (found) { - TRACE("bt OK"); - bluetoothState = BLUETOOTH_OK; - } - else { - TRACE("bt failure"); - bluetoothInit(BLUETOOTH_FACTORY_BAUDRATE); - const char btMessage[] = "TTM:BPS-115200"; - bluetoothWriteString(btMessage); - bluetoothState = BLUETOOTH_WAIT_BAUDRATE_CHANGE; - waitEnd = get_tmr10ms() + 250; // 2.5s - } - } - } - else if (bluetoothState == BLUETOOTH_WAIT_BAUDRATE_CHANGE) { - if (get_tmr10ms() > waitEnd) { - bluetoothState = BLUETOOTH_INIT; - } - } - } - - bluetoothWriteWakeup(); - } -#endif // #if defined(BLUETOOTH_CLI_PASSTHROUGH) -} - -uint8_t bluetoothReady() -{ - return (bluetoothState == BLUETOOTH_OK); -} - -int bluetoothRead(void * buffer, int len) -{ - int result = 0; - uint8_t * data = (uint8_t *)buffer; - while (result < len) { - uint8_t byte; - if (!btRxFifo.pop(byte)) { - break; - } - data[result++] = byte; - } - return result; -} diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/horus/board.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/horus/board.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/horus/board.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/horus/board.cpp 2017-11-10 17:23:25.000000000 +0000 @@ -80,6 +80,7 @@ if (pre_scale == 10) { pre_scale = 0; DEBUG_TIMER_START(debugTimerPer10ms); + DEBUG_TIMER_SAMPLE(debugTimerPer10msPeriod); per10ms(); DEBUG_TIMER_STOP(debugTimerPer10ms); } @@ -100,6 +101,29 @@ extern "C" void initialise_monitor_handles(); #endif +#if defined(PCBX10) +void sportUpdateInit() +{ + GPIO_InitTypeDef GPIO_InitStructure; + GPIO_InitStructure.GPIO_Pin = SPORT_UPDATE_PWR_GPIO_PIN; + GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT; + GPIO_InitStructure.GPIO_Speed = GPIO_Speed_2MHz; + GPIO_InitStructure.GPIO_OType = GPIO_OType_PP; + GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP; + GPIO_Init(SPORT_UPDATE_PWR_GPIO, &GPIO_InitStructure); +} + +void sportUpdatePowerOn() +{ + GPIO_SetBits(SPORT_UPDATE_PWR_GPIO, SPORT_UPDATE_PWR_GPIO_PIN); +} + +void sportUpdatePowerOff() +{ + GPIO_ResetBits(SPORT_UPDATE_PWR_GPIO, SPORT_UPDATE_PWR_GPIO_PIN); +} +#endif + void boardInit() { #if defined(SEMIHOSTING) @@ -119,15 +143,18 @@ SERIAL_RCC_AHB1Periph | TELEMETRY_RCC_AHB1Periph | TRAINER_RCC_AHB1Periph | + BT_RCC_AHB1Periph | AUDIO_RCC_AHB1Periph | HAPTIC_RCC_AHB1Periph | INTMODULE_RCC_AHB1Periph | EXTMODULE_RCC_AHB1Periph | GPS_RCC_AHB1Periph | + SPORT_UPDATE_RCC_AHB1Periph | BL_RCC_AHB1Periph, ENABLE); RCC_APB1PeriphClockCmd(INTERRUPT_1MS_RCC_APB1Periph | + ADC_RCC_APB1Periph | TIMER_2MHz_RCC_APB1Periph | AUDIO_RCC_APB1Periph | SERIAL_RCC_APB1Periph | @@ -145,6 +172,7 @@ HAPTIC_RCC_APB2Periph | INTMODULE_RCC_APB2Periph | EXTMODULE_RCC_APB2Periph | + BT_RCC_APB2Periph | BL_RCC_APB2Periph, ENABLE); @@ -180,10 +208,10 @@ hapticInit(); #if defined(BLUETOOTH) - bluetoothInit(BLUETOOTH_FACTORY_BAUDRATE); + bluetoothInit(BLUETOOTH_DEFAULT_BAUDRATE); #endif -#if defined(PCBX12S) +#if defined(INTERNAL_GPS) gpsInit(GPS_USART_BAUDRATE); #endif @@ -193,6 +221,7 @@ #if defined(PCBX10) ledInit(); + sportUpdateInit(); #endif ledBlue(); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/horus/board.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/horus/board.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/horus/board.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/horus/board.h 2017-12-17 16:22:27.000000000 +0000 @@ -22,6 +22,7 @@ #define _BOARD_HORUS_H_ #include "stddef.h" +#include "stdbool.h" #if defined(__cplusplus) && !defined(SIMU) extern "C" { @@ -62,6 +63,7 @@ #pragma clang diagnostic pop #endif +#include "usb_driver.h" #if !defined(SIMU) #include "usbd_cdc_core.h" @@ -99,7 +101,12 @@ extern uint16_t sessionTimer; #define SLAVE_MODE() (g_model.trainerMode == TRAINER_MODE_SLAVE) -#define TRAINER_CONNECTED() (GPIO_ReadInputDataBit(TRAINER_DETECT_GPIO, TRAINER_DETECT_GPIO_PIN) == Bit_RESET) + +#if defined(PCBX10) + #define TRAINER_CONNECTED() (GPIO_ReadInputDataBit(TRAINER_DETECT_GPIO, TRAINER_DETECT_GPIO_PIN) == Bit_SET) +#else + #define TRAINER_CONNECTED() (GPIO_ReadInputDataBit(TRAINER_DETECT_GPIO, TRAINER_DETECT_GPIO_PIN) == Bit_RESET) +#endif // Board driver void boardInit(void); @@ -192,11 +199,8 @@ void disable_dsm2(uint32_t module_index); void init_crossfire(uint32_t module_index); void disable_crossfire(uint32_t module_index); - -#if defined(MULTIMODULE) -void init_multimodule(uint32_t module_index); -void disable_multimodule(uint32_t module_index); -#endif +void init_sbusOut(uint32_t module_index); +void disable_sbusOut(uint32_t module_index); // Trainer driver void init_trainer_ppm(void); @@ -218,7 +222,7 @@ KEY_RIGHT = KEY_TELEM, KEY_RADIO, KEY_LEFT = KEY_RADIO, - + TRM_BASE, TRM_LH_DWN = TRM_BASE, TRM_LH_UP, @@ -233,7 +237,7 @@ TRM_RS_DWN, TRM_RS_UP, TRM_LAST = TRM_RS_UP, - + NUM_KEYS }; @@ -329,8 +333,10 @@ #define NUM_XPOTS NUM_POTS #if defined(PCBX10) #define NUM_SLIDERS 2 + #define NUM_PWMANALOGS 4 #else #define NUM_SLIDERS 4 + #define NUM_PWMANALOGS 0 #endif enum Analogs { STICK1, @@ -390,6 +396,14 @@ void adcRead(void); uint16_t getAnalogValue(uint8_t index); uint16_t getBatteryVoltage(); // returns current battery voltage in 10mV steps +#if NUM_PWMANALOGS > 0 +extern uint8_t analogs_pwm_disabled; +#define ANALOGS_PWM_ENABLED() (analogs_pwm_disabled == false) +void pwmInit(void); +void pwmRead(uint16_t * values); +void pwmCheck(); +extern volatile uint32_t pwm_interrupt_count; +#endif #if defined(__cplusplus) && !defined(SIMU) extern "C" { @@ -407,7 +421,7 @@ #if defined(SIMU) || defined(NO_UNEXPECTED_SHUTDOWN) #define UNEXPECTED_SHUTDOWN() (false) #else - #define UNEXPECTED_SHUTDOWN() (powerupReason == DIRTY_SHUTDOWN) + #define UNEXPECTED_SHUTDOWN() ((powerupReason == DIRTY_SHUTDOWN) || WAS_RESET_BY_WATCHDOG_OR_SOFTWARE()) #endif // Led driver @@ -443,18 +457,17 @@ #else void backlightEnable(uint8_t dutyCycle); #endif -#define BACKLIGHT_ENABLE() backlightEnable(unexpectedShutdown ? 100 : 100-g_eeGeneral.backlightBright) -#define BACKLIGHT_DISABLE() backlightEnable(unexpectedShutdown ? 100 : g_eeGeneral.blOffBright) +#define BACKLIGHT_LEVEL_MAX 100 +#if defined(PCBX12S) +#define BACKLIGHT_LEVEL_MIN 5 +#else +#define BACKLIGHT_LEVEL_MIN 46 +#endif +#define BACKLIGHT_ENABLE() backlightEnable(unexpectedShutdown ? BACKLIGHT_LEVEL_MAX : BACKLIGHT_LEVEL_MAX-g_eeGeneral.backlightBright) +#define BACKLIGHT_DISABLE() backlightEnable(unexpectedShutdown ? BACKLIGHT_LEVEL_MAX : g_eeGeneral.blOffBright) #define isBacklightEnabled() true -// USB driver -int usbPlugged(); -void usbInit(); -void usbStart(); -void usbStop(); -uint8_t usbStarted(); -void usbSerialPutc(uint8_t c); -#if defined(USB_JOYSTICK) && !defined(SIMU) +#if !defined(SIMU) void usbJoystickUpdate(); #endif #if defined(PCBX12S) @@ -462,7 +475,7 @@ #define USB_MANUFACTURER 'F', 'r', 'S', 'k', 'y', ' ', ' ', ' ' /* 8 bytes */ #define USB_PRODUCT 'H', 'o', 'r', 'u', 's', ' ', ' ', ' ' /* 8 Bytes */ #elif defined(PCBX10) - #define USB_NAME "FrSky HX10" + #define USB_NAME "FrSky X10" #define USB_MANUFACTURER 'F', 'r', 'S', 'k', 'y', ' ', ' ', ' ' /* 8 bytes */ #define USB_PRODUCT 'X', '1', '0', ' ', ' ', ' ', ' ', ' ' /* 8 Bytes */ #endif @@ -493,10 +506,18 @@ void telemetryPortSetDirectionOutput(void); void sportSendBuffer(uint8_t * buffer, uint32_t count); uint8_t telemetryGetByte(uint8_t * byte); +extern uint32_t telemetryErrors; // Sport update driver +#if defined(PCBX10) +void sportUpdatePowerOn(void); +void sportUpdatePowerOff(void); +#define SPORT_UPDATE_POWER_ON() sportUpdatePowerOn() +#define SPORT_UPDATE_POWER_OFF() sportUpdatePowerOff() +#else #define SPORT_UPDATE_POWER_ON() EXTERNAL_MODULE_ON() #define SPORT_UPDATE_POWER_OFF() EXTERNAL_MODULE_OFF() +#endif // Haptic driver void hapticInit(void); @@ -526,14 +547,11 @@ int sbusGetByte(uint8_t * byte); // BT driver +#define BLUETOOTH_FACTORY_BAUDRATE 57600 #define BLUETOOTH_DEFAULT_BAUDRATE 115200 -#define BLUETOOTH_FACTORY_BAUDRATE 9600 -uint8_t bluetoothReady(void); void bluetoothInit(uint32_t baudrate); -void bluetoothWrite(const void * buffer, int len); -void bluetoothWriteString(const char * str); -int bluetoothRead(void * buffer, int len); -void bluetoothWakeup(void); +void bluetoothWriteWakeup(void); +uint8_t bluetoothIsWriting(void); void bluetoothDone(void); extern uint8_t currentTrainerMode; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/horus/CMakeLists.txt opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/horus/CMakeLists.txt --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/horus/CMakeLists.txt 2017-04-27 08:57:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/horus/CMakeLists.txt 2017-10-31 16:16:43.000000000 +0000 @@ -1,5 +1,4 @@ option(DISK_CACHE "Enable SD card disk cache" YES) -option(BLUETOOTH_CLI_PASSTHROUGH "Enable direct communicaton with Bluetooth module from CLI" NO) option(UNEXPECTED_SHUTDOWN "Enable the Unexpected Shutdown screen" YES) set(PWR_BUTTON "PRESS" CACHE STRING "Pwr button type (PRESS/SWITCH)") @@ -30,6 +29,7 @@ ${TARGET_SRC} ../common/arm/stm32/audio_dac_driver.cpp ../common/arm/stm32/adc_driver.cpp + pwm_driver.cpp ) set(FIRMWARE_DEPENDENCIES ${FIRMWARE_DEPENDENCIES} x10_bitmaps) set(LUA_EXPORT lua_export_x10) @@ -103,14 +103,19 @@ add_definitions(-DINTERNAL_GPS) message("Horus: Internal GPS enabled") endif() + set(SERIAL2_DRIVER ../common/arm/stm32/serial2_driver.cpp) + set(GVAR_SCREEN model_gvars.cpp) + set(TARGET_SRC ${TARGET_SRC} board.cpp led_driver.cpp extmodule_driver.cpp + ../common/arm/stm32/bluetooth_driver.cpp ) + set(FIRMWARE_TARGET_SRC ${FIRMWARE_TARGET_SRC} sdio_sd.c @@ -120,17 +125,14 @@ sdram_driver.c startup_stm32f42_43xxx.s ) -if(PCB STREQUAL X12S) - set(FIRMWARE_TARGET_SRC - ${FIRMWARE_TARGET_SRC} - bluetooth_driver.cpp - ) - add_definitions(-DBLUETOOTH) -endif() -if(BLUETOOTH_CLI_PASSTHROUGH) - add_definitions(-DBLUETOOTH_CLI_PASSTHROUGH) - message("Horus: Bluetooth pass-trough enabled") -endif() + +add_definitions(-DBLUETOOTH) + +set(SRC + ${SRC} + bluetooth.cpp + ) + set(STM32LIB_SRC STM32F4xx_StdPeriph_Driver/src/stm32f4xx_sdio.c STM32F4xx_StdPeriph_Driver/src/stm32f4xx_fmc.c diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/horus/extmodule_driver.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/horus/extmodule_driver.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/horus/extmodule_driver.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/horus/extmodule_driver.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -91,7 +91,7 @@ EXTMODULE_TIMER->CR1 &= ~TIM_CR1_CEN; // Stop timer EXTMODULE_TIMER->PSC = EXTMODULE_TIMER_FREQ / 2000000 - 1; // 0.5uS (2Mhz) EXTMODULE_TIMER->ARR = 45000; -#if PCBREV >= 13 +#if defined(PCBX10) || PCBREV >= 13 EXTMODULE_TIMER->CCMR2 = TIM_CCMR2_OC3M_1 | TIM_CCMR2_OC3M_2; // PWM mode 1 EXTMODULE_TIMER->BDTR = TIM_BDTR_MOE; EXTMODULE_TIMER->EGR = 1; // Reloads register values now @@ -133,7 +133,7 @@ EXTMODULE_TIMER->PSC = EXTMODULE_TIMER_FREQ / 2000000 - 1; // 0.5uS (2Mhz) EXTMODULE_TIMER->ARR = 18000; -#if PCBREV >= 13 +#if defined(PCBX10) || PCBREV >= 13 EXTMODULE_TIMER->CCER = TIM_CCER_CC3E | TIM_CCER_CC3NE; EXTMODULE_TIMER->BDTR = TIM_BDTR_MOE; // Enable outputs EXTMODULE_TIMER->CCR3 = 18; @@ -180,7 +180,7 @@ EXTMODULE_TIMER->PSC = EXTMODULE_TIMER_FREQ / 2000000 - 1; // 0.5uS (2Mhz) EXTMODULE_TIMER->ARR = 44000; // 22mS -#if PCBREV >= 13 +#if defined(PCBX10) || PCBREV >= 13 EXTMODULE_TIMER->CCER = TIM_CCER_CC3E | TIM_CCER_CC3P; EXTMODULE_TIMER->BDTR = TIM_BDTR_MOE; // Enable outputs EXTMODULE_TIMER->CCR3 = 0; @@ -240,7 +240,7 @@ void extmoduleSendNextFrame() { if (s_current_protocol[EXTERNAL_MODULE] == PROTO_PPM) { -#if PCBREV >= 13 +#if defined(PCBX10) || PCBREV >= 13 EXTMODULE_TIMER->CCR3 = GET_PPM_DELAY(EXTERNAL_MODULE)*2; EXTMODULE_TIMER->CCER = TIM_CCER_CC3E | (GET_PPM_POLARITY(EXTERNAL_MODULE) ? TIM_CCER_CC3P : 0); EXTMODULE_TIMER->CCR2 = *(modulePulsesData[EXTERNAL_MODULE].ppm.ptr - 1) - 4000; // 2mS in advance @@ -261,7 +261,7 @@ else if (s_current_protocol[EXTERNAL_MODULE] == PROTO_PXX) { EXTMODULE_TIMER->CCR2 = *(modulePulsesData[EXTERNAL_MODULE].pxx.ptr - 1) - 4000; // 2mS in advance EXTMODULE_DMA_STREAM->CR &= ~DMA_SxCR_EN; // Disable DMA -#if PCBREV >= 13 +#if defined(PCBX10) || PCBREV >= 13 EXTMODULE_DMA_STREAM->CR |= EXTMODULE_DMA_CHANNEL | DMA_SxCR_DIR_0 | DMA_SxCR_MINC | DMA_SxCR_PSIZE_0 | DMA_SxCR_MSIZE_0 | DMA_SxCR_PL_0 | DMA_SxCR_PL_1; #else EXTMODULE_DMA_STREAM->CR |= EXTMODULE_DMA_CHANNEL | DMA_SxCR_DIR_0 | DMA_SxCR_MINC | DMA_SxCR_PSIZE_1 | DMA_SxCR_MSIZE_1 | DMA_SxCR_PL_0 | DMA_SxCR_PL_1; @@ -271,13 +271,17 @@ EXTMODULE_DMA_STREAM->NDTR = modulePulsesData[EXTERNAL_MODULE].pxx.ptr - modulePulsesData[EXTERNAL_MODULE].pxx.pulses; EXTMODULE_DMA_STREAM->CR |= DMA_SxCR_EN | DMA_SxCR_TCIE; // Enable DMA } - else if (IS_DSM2_PROTOCOL(s_current_protocol[EXTERNAL_MODULE]) || IS_MULTIMODULE_PROTOCOL(s_current_protocol[EXTERNAL_MODULE])) { + else if (IS_DSM2_PROTOCOL(s_current_protocol[EXTERNAL_MODULE]) || IS_MULTIMODULE_PROTOCOL(s_current_protocol[EXTERNAL_MODULE]) || IS_SBUS_PROTOCOL(s_current_protocol[EXTERNAL_MODULE])) { EXTMODULE_TIMER->CCR2 = *(modulePulsesData[EXTERNAL_MODULE].dsm2.ptr - 1) - 4000; // 2mS in advance EXTMODULE_DMA_STREAM->CR &= ~DMA_SxCR_EN; // Disable DMA -#if PCBREV >= 13 +#if defined(PCBX10) || PCBREV >= 13 EXTMODULE_DMA_STREAM->CR |= EXTMODULE_DMA_CHANNEL | DMA_SxCR_DIR_0 | DMA_SxCR_MINC | DMA_SxCR_PSIZE_0 | DMA_SxCR_MSIZE_0 | DMA_SxCR_PL_0 | DMA_SxCR_PL_1; + if (IS_SBUS_PROTOCOL(s_current_protocol[EXTERNAL_MODULE])) + EXTMODULE_TIMER->CCER = TIM_CCER_CC3E | (GET_SBUS_POLARITY(EXTERNAL_MODULE) ? TIM_CCER_CC3P : 0); // reverse polarity for Sbus if needed #else EXTMODULE_DMA_STREAM->CR |= EXTMODULE_DMA_CHANNEL | DMA_SxCR_DIR_0 | DMA_SxCR_MINC | DMA_SxCR_PSIZE_1 | DMA_SxCR_MSIZE_1 | DMA_SxCR_PL_0 | DMA_SxCR_PL_1; + if (IS_SBUS_PROTOCOL(s_current_protocol[EXTERNAL_MODULE])) + EXTMODULE_TIMER->CCER = TIM_CCER_CC1E | (GET_SBUS_POLARITY(EXTERNAL_MODULE) ? TIM_CCER_CC1P : 0); // reverse polarity for Sbus if needed #endif EXTMODULE_DMA_STREAM->PAR = CONVERT_PTR_UINT(&EXTMODULE_TIMER->ARR); EXTMODULE_DMA_STREAM->M0AR = CONVERT_PTR_UINT(modulePulsesData[EXTERNAL_MODULE].dsm2.pulses); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/horus/hal.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/horus/hal.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/horus/hal.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/horus/hal.h 2017-10-31 16:16:43.000000000 +0000 @@ -39,16 +39,20 @@ #define KEYS_GPIO_REG_RIGHT GPIOC->IDR #define KEYS_GPIO_PIN_RIGHT GPIO_Pin_4 // PC.04 #elif defined(PCBX10) - #define KEYS_GPIO_REG_PGDN GPIOI->IDR - #define KEYS_GPIO_PIN_PGDN GPIO_Pin_11 // PI.11 - #define KEYS_GPIO_REG_LEFT GPIOI->IDR - #define KEYS_GPIO_PIN_LEFT GPIO_Pin_7 // PI.07 + // #define KEYS_GPIO_REG_UNUSED GPIOH->IDR + // #define KEYS_GPIO_PIN_UNUSED GPIO_Pin_14 // PH.14 + // #define KEYS_GPIO_REG_UNUSED GPIOH->IDR + // #define KEYS_GPIO_PIN_UNUSED GPIO_Pin_15 // PH.15 #define KEYS_GPIO_REG_ENTER GPIOI->IDR #define KEYS_GPIO_PIN_ENTER GPIO_Pin_8 // PI.08 + #define KEYS_GPIO_REG_PGDN GPIOI->IDR + #define KEYS_GPIO_PIN_PGDN GPIO_Pin_11 // PI.11 #define KEYS_GPIO_REG_UP GPIOI->IDR #define KEYS_GPIO_PIN_UP GPIO_Pin_4 // PI.04 #define KEYS_GPIO_REG_DOWN GPIOI->IDR #define KEYS_GPIO_PIN_DOWN GPIO_Pin_6 // PI.06 + #define KEYS_GPIO_REG_LEFT GPIOI->IDR + #define KEYS_GPIO_PIN_LEFT GPIO_Pin_7 // PI.07 #define KEYS_GPIO_REG_RIGHT GPIOI->IDR #define KEYS_GPIO_PIN_RIGHT GPIO_Pin_5 // PI.05 #endif @@ -165,14 +169,15 @@ #define KEYS_GPIOD_PINS (SWITCHES_GPIO_PIN_C_H | TRIMS_GPIO_PIN_RHL | TRIMS_GPIO_PIN_RHR | TRIMS_GPIO_PIN_LSD) #define KEYS_GPIOE_PINS (SWITCHES_GPIO_PIN_E_L) #define KEYS_GPIOG_PINS (SWITCHES_GPIO_PIN_D_L | SWITCHES_GPIO_PIN_G_H | SWITCHES_GPIO_PIN_G_L | SWITCHES_GPIO_PIN_H | TRIMS_GPIO_PIN_LVD) - #define KEYS_GPIOH_PINS (SWITCHES_GPIO_PIN_A_H | SWITCHES_GPIO_PIN_B_H | SWITCHES_GPIO_PIN_E_H | SWITCHES_GPIO_PIN_F | ROTARY_ENCODER_GPIO_PIN_A | ROTARY_ENCODER_GPIO_PIN_B | SWITCHES_GPIO_PIN_GMBR | SWITCHES_GPIO_PIN_GMBL) - #define KEYS_GPIOI_PINS (KEYS_GPIO_PIN_RIGHT | KEYS_GPIO_PIN_UP | KEYS_GPIO_PIN_ENTER | KEYS_GPIO_PIN_PGDN | KEYS_GPIO_PIN_LEFT | KEYS_GPIO_PIN_DOWN | SWITCHES_GPIO_PIN_A_L) + #define KEYS_GPIOH_PINS (GPIO_Pin_3 | GPIO_Pin_4 | GPIO_Pin_9 | GPIO_Pin_10 | GPIO_Pin_11 | GPIO_Pin_12) // | GPIO_Pin_14 | GPIO_Pin_15) + #define KEYS_GPIOI_PINS (GPIO_Pin_4 | GPIO_Pin_5 | GPIO_Pin_6 | GPIO_Pin_7 | GPIO_Pin_8 | GPIO_Pin_11 | GPIO_Pin_15) #define KEYS_GPIOJ_PINS (SWITCHES_GPIO_PIN_D_H | TRIMS_GPIO_PIN_LVU | TRIMS_GPIO_PIN_RVD | TRIMS_GPIO_PIN_RVU | TRIMS_GPIO_PIN_LSU) #endif // ADC #if defined(PCBX12S) #define ADC_RCC_AHB1Periph (RCC_AHB1Periph_GPIOE | RCC_AHB1Periph_GPIOF | RCC_AHB1Periph_DMA2) + #define ADC_RCC_APB1Periph 0 #define ADC_RCC_APB2Periph (RCC_APB2Periph_SPI4 | RCC_APB2Periph_ADC3) #define ADC_SPI SPI4 #define ADC_GPIO_AF GPIO_AF_SPI4 @@ -194,34 +199,41 @@ #define ADC_SAMPTIME 3 #elif defined(PCBX10) #define ADC_RCC_AHB1Periph (RCC_AHB1Periph_GPIOA | RCC_AHB1Periph_GPIOC | RCC_AHB1Periph_GPIOF | RCC_AHB1Periph_DMA2) + #define ADC_RCC_APB1Periph (RCC_APB1Periph_TIM5) #define ADC_RCC_APB2Periph (RCC_APB2Periph_ADC3) - #define ADC_GPIO_PIN_STICK_LH GPIO_Pin_0 // PC.00 - #define ADC_GPIO_PIN_STICK_LV GPIO_Pin_1 // PC.01 - #define ADC_GPIO_PIN_STICK_RH GPIO_Pin_2 // PC.02 - #define ADC_GPIO_PIN_STICK_RV GPIO_Pin_3 // PC.03 + #define ADC_GPIO_PIN_STICK_LH GPIO_Pin_0 // PA.00 + #define ADC_GPIO_PIN_STICK_LV GPIO_Pin_1 // PA.01 + #define ADC_GPIO_PIN_STICK_RH GPIO_Pin_2 // PA.02 + #define ADC_GPIO_PIN_STICK_RV GPIO_Pin_3 // PA.03 + #define ADC_GPIO_PIN_POT1 GPIO_Pin_0 // PC.00 + #define ADC_GPIO_PIN_POT2 GPIO_Pin_1 // PC.01 + #define ADC_GPIO_PIN_POT3 GPIO_Pin_2 // PC.02 #define ADC_GPIO_PIN_SLIDER1 GPIO_Pin_6 // PF.06 - #define ADC_GPIO_PIN_SLIDER2 GPIO_Pin_3 // PA.03 + #define ADC_GPIO_PIN_SLIDER2 GPIO_Pin_3 // PC.03 #define ADC_GPIO_PIN_BATT GPIO_Pin_7 // PF.07 - #define ADC_GPIO_PIN_POT3 GPIO_Pin_0 // PA.00 - #define ADC_GPIO_PIN_POT1 GPIO_Pin_2 // PA.02 - #define ADC_GPIO_PIN_POT2 GPIO_Pin_1 // PA.01 #define ADC_GPIO_PIN_EXT1 GPIO_Pin_8 // PF.08 #define ADC_GPIO_PIN_EXT2 GPIO_Pin_9 // PF.09 - #define ADC_GPIOA_PINS (GPIO_Pin_0 | GPIO_Pin_1 | GPIO_Pin_2 | GPIO_Pin_3) + #define PWM_TIMER TIM5 + #define PWM_GPIO GPIOA + #define PWM_GPIO_AF GPIO_AF_TIM5 + #define PWM_IRQHandler TIM5_IRQHandler + #define PWM_IRQn TIM5_IRQn + #define PWM_GPIOA_PINS (GPIO_Pin_0 | GPIO_Pin_1 | GPIO_Pin_2 | GPIO_Pin_3) + #define ADC_GPIOA_PINS (ANALOGS_PWM_ENABLED() ? 0 : (GPIO_Pin_0 | GPIO_Pin_1 | GPIO_Pin_2 | GPIO_Pin_3)) #define ADC_GPIOC_PINS (GPIO_Pin_0 | GPIO_Pin_1 | GPIO_Pin_2 | GPIO_Pin_3) - #define ADC_GPIOF_PINS (GPIO_Pin_6 | GPIO_Pin_7 | GPIO_Pin_8 | GPIO_Pin_9) - #define ADC_CHANNEL_STICK_LH ADC_Channel_10 // ADC1_IN10 - #define ADC_CHANNEL_STICK_LV ADC_Channel_11 // ADC1_IN11 - #define ADC_CHANNEL_STICK_RH ADC_Channel_12 // ADC1_IN12 - #define ADC_CHANNEL_STICK_RV ADC_Channel_13 // ADC1_IN13 - #define ADC_CHANNEL_SLIDER1 ADC_Channel_4 // ADC1_IN4 - #define ADC_CHANNEL_SLIDER2 ADC_Channel_3 // ADC1_IN3 - #define ADC_CHANNEL_BATT ADC_Channel_5 // ADC1_IN5 - #define ADC_CHANNEL_POT3 ADC_Channel_0 // ADC1_IN0 - #define ADC_CHANNEL_POT1 ADC_Channel_2 // ADC1_IN2 - #define ADC_CHANNEL_POT2 ADC_Channel_1 // ADC1_IN1 - #define ADC_CHANNEL_EXT1 ADC_Channel_6 // ADC1_IN6 - #define ADC_CHANNEL_EXT2 ADC_Channel_7 // ADC1_IN7 + #define ADC_GPIOF_PINS (GPIO_Pin_6 | GPIO_Pin_7) // | GPIO_Pin_8 | GPIO_Pin_9) + #define ADC_CHANNEL_STICK_LH ADC_Channel_0 // ADC3_IN0 + #define ADC_CHANNEL_STICK_LV ADC_Channel_1 // ADC3_IN1 + #define ADC_CHANNEL_STICK_RH ADC_Channel_2 // ADC3_IN2 + #define ADC_CHANNEL_STICK_RV ADC_Channel_3 // ADC3_IN3 + #define ADC_CHANNEL_POT1 ADC_Channel_10 // ADC3_IN10 + #define ADC_CHANNEL_POT2 ADC_Channel_11 // ADC3_IN11 + #define ADC_CHANNEL_POT3 ADC_Channel_12 // ADC3_IN12 + #define ADC_CHANNEL_SLIDER1 ADC_Channel_4 // ADC3_IN4 + #define ADC_CHANNEL_SLIDER2 ADC_Channel_13 // ADC3_IN13 + #define ADC_CHANNEL_BATT ADC_Channel_5 // ADC3_IN5 + #define ADC_CHANNEL_EXT1 ADC_Channel_6 // ADC3_IN6 + #define ADC_CHANNEL_EXT2 ADC_Channel_7 // ADC3_IN7 #define ADC_MAIN ADC3 #define ADC_SAMPTIME 3 #define ADC_DMA DMA2 @@ -238,9 +250,11 @@ #define PWR_SWITCH_GPIO_PIN GPIO_Pin_0 // PJ.00 #if defined(PCBX10) - #define SPORT_PWR_RCC_AHB1Periph RCC_AHB1Periph_GPIOH - #define SPORT_PWR_GPIO GPIOH - #define SPORT_PWR_GPIO_PIN GPIO_Pin_13 // PH.13 + #define SPORT_UPDATE_RCC_AHB1Periph RCC_AHB1Periph_GPIOH + #define SPORT_UPDATE_PWR_GPIO GPIOH + #define SPORT_UPDATE_PWR_GPIO_PIN GPIO_Pin_13 // PH.13 +#else + #define SPORT_UPDATE_RCC_AHB1Periph 0 #endif // PCBREV @@ -256,9 +270,9 @@ #elif defined(PCBX10) #define LED_RCC_AHB1Periph RCC_AHB1Periph_GPIOE #define LED_GPIO GPIOE - #define LED_RED_GPIO_PIN GPIO_Pin_5 + #define LED_RED_GPIO_PIN GPIO_Pin_2 #define LED_GREEN_GPIO_PIN GPIO_Pin_4 - #define LED_BLUE_GPIO_PIN GPIO_Pin_6 + #define LED_BLUE_GPIO_PIN GPIO_Pin_5 #define LED_GPIO_PIN (LED_RED_GPIO_PIN | LED_GREEN_GPIO_PIN | LED_BLUE_GPIO_PIN) #endif @@ -470,14 +484,20 @@ #define HAPTIC_GPIO_TIMER TIM9 #define HAPTIC_GPIO_AF GPIO_AF_TIM9 #define HAPTIC_GPIO_PinSource GPIO_PinSource2 + #define HAPTIC_TIMER_OUTPUT_ENABLE TIM_CCER_CC1E + #define HAPTIC_TIMER_MODE TIM_CCMR1_OC1M_1 | TIM_CCMR1_OC1M_2 + #define HAPTIC_TIMER_COMPARE_VALUE HAPTIC_GPIO_TIMER->CCR1 #elif defined(PCBX10) - #define HAPTIC_RCC_AHB1Periph RCC_AHB1Periph_GPIOB - #define HAPTIC_RCC_APB2Periph RCC_APB2ENR_TIM8EN - #define HAPTIC_GPIO GPIOB - #define HAPTIC_GPIO_PIN GPIO_Pin_0 // PB.00 - #define HAPTIC_GPIO_TIMER TIM8 - #define HAPTIC_GPIO_AF GPIO_AF_TIM8 - #define HAPTIC_GPIO_PinSource GPIO_PinSource0 + #define HAPTIC_RCC_AHB1Periph RCC_AHB1Periph_GPIOE + #define HAPTIC_RCC_APB2Periph RCC_APB2ENR_TIM9EN + #define HAPTIC_GPIO GPIOE + #define HAPTIC_GPIO_PIN GPIO_Pin_6 // PE.06 + #define HAPTIC_GPIO_TIMER TIM9 + #define HAPTIC_GPIO_AF GPIO_AF_TIM9 + #define HAPTIC_GPIO_PinSource GPIO_PinSource6 + #define HAPTIC_TIMER_OUTPUT_ENABLE TIM_CCER_CC2E + #define HAPTIC_TIMER_MODE TIM_CCMR1_OC2M_1 | TIM_CCMR1_OC2M_2 + #define HAPTIC_TIMER_COMPARE_VALUE HAPTIC_GPIO_TIMER->CCR2 #endif // Internal Module @@ -498,7 +518,14 @@ #define INTMODULE_DMA_STREAM_IRQHandler DMA2_Stream7_IRQHandler #define INTMODULE_DMA_FLAG_TC DMA_IT_TCIF7 #define INTMODULE_DMA_CHANNEL DMA_Channel_4 -#if PCBREV >= 13 +#if defined(PCBX12S) + #define INTMODULE_BOOT_GPIO GPIOI + #define INTMODULE_BOOT_GPIO_PIN GPIO_PIN_9 // PC.02 +#elif defined(PCBX10) + #define INTMODULE_BOOT_GPIO GPIOI + #define INTMODULE_BOOT_GPIO_PIN GPIO_PIN_9 // PI.09 +#endif +#if defined(PCBX10) || PCBREV >= 13 #define INTMODULE_RCC_APB1Periph RCC_APB1Periph_TIM2 #define INTMODULE_RCC_APB2Periph RCC_APB2Periph_USART1 #define INTMODULE_TIMER TIM2 @@ -517,7 +544,7 @@ // External Module #define EXTMODULE_PWR_GPIO GPIOB #define EXTMODULE_PWR_GPIO_PIN GPIO_Pin_3 // PB.03 -#if PCBREV >= 13 +#if defined(PCBX10) || PCBREV >= 13 #define EXTMODULE_RCC_AHB1Periph (RCC_AHB1Periph_GPIOA | RCC_AHB1Periph_GPIOB | RCC_AHB1Periph_DMA2) #define EXTMODULE_RCC_APB1Periph 0 #define EXTMODULE_RCC_APB2Periph RCC_APB2Periph_TIM1 @@ -553,6 +580,11 @@ #define EXTMODULE_DMA_FLAG_TC DMA_IT_TCIF7 #endif +// Heartbeat (not used) +#define HEARTBEAT_RCC_AHB1Periph RCC_AHB1Periph_GPIOD +#define HEARTBEAT_GPIO GPIOD +#define HEARTBEAT_GPIO_PIN GPIO_Pin_12 // PD.12 + // Trainer Port #define TRAINER_RCC_AHB1Periph (RCC_AHB1Periph_GPIOB | RCC_AHB1Periph_GPIOC | RCC_AHB1Periph_DMA1) #define TRAINER_RCC_APB1Periph RCC_APB1Periph_TIM3 @@ -586,14 +618,17 @@ #define TIMER_2MHz_TIMER TIM7 // Bluetooth +#define BT_RCC_APB2Periph RCC_APB2Periph_USART6 +#define BT_USART USART6 +#define BT_GPIO_AF GPIO_AF_USART6 +#define BT_USART_IRQn USART6_IRQn +#define BT_GPIO_TXRX GPIOG +#define BT_TX_GPIO_PIN GPIO_Pin_14 // PG.14 +#define BT_RX_GPIO_PIN GPIO_Pin_9 // PG.09 +#define BT_TX_GPIO_PinSource GPIO_PinSource14 +#define BT_RX_GPIO_PinSource GPIO_PinSource9 +#define BT_USART_IRQHandler USART6_IRQHandler #if defined(PCBX12S) - #define BT_RCC_APB2Periph RCC_APB2Periph_USART6 - #define BT_USART USART6 - #define BT_GPIO_AF GPIO_AF_USART6 - #define BT_USART_IRQn USART6_IRQn - #define BT_GPIO_TXRX GPIOG - #define BT_TX_GPIO_PIN GPIO_Pin_14 // PG.14 - #define BT_RX_GPIO_PIN GPIO_Pin_9 // PG.09 #if PCBREV >= 13 #define BT_RCC_AHB1Periph (RCC_AHB1Periph_GPIOI | RCC_AHB1Periph_GPIOG) #define BT_EN_GPIO GPIOI @@ -607,21 +642,28 @@ #define BT_BRTS_GPIO_PIN GPIO_Pin_10 // PG.10 #define BT_BCTS_GPIO GPIOG #define BT_BCTS_GPIO_PIN GPIO_Pin_11 // PG.11 - #define BT_TX_GPIO_PinSource GPIO_PinSource14 - #define BT_RX_GPIO_PinSource GPIO_PinSource9 +#elif defined(PCBX10) + #define BT_RCC_AHB1Periph RCC_AHB1Periph_GPIOG + #define BT_EN_GPIO GPIOG + #define BT_EN_GPIO_PIN GPIO_Pin_10 // PG.10 #endif // GPS -#define GPS_RCC_AHB1Periph RCC_AHB1Periph_GPIOA -#define GPS_RCC_APB1Periph RCC_APB1Periph_UART4 -#define GPS_USART UART4 -#define GPS_GPIO_AF GPIO_AF_UART4 -#define GPS_USART_IRQn UART4_IRQn -#define GPS_USART_IRQHandler UART4_IRQHandler -#define GPS_UART_GPIO GPIOA -#define GPS_TX_GPIO_PIN GPIO_Pin_0 // PA.00 -#define GPS_RX_GPIO_PIN GPIO_Pin_1 // PA.01 -#define GPS_TX_GPIO_PinSource GPIO_PinSource0 -#define GPS_RX_GPIO_PinSource GPIO_PinSource1 +#if defined(PCBX12S) + #define GPS_RCC_AHB1Periph RCC_AHB1Periph_GPIOA + #define GPS_RCC_APB1Periph RCC_APB1Periph_UART4 + #define GPS_USART UART4 + #define GPS_GPIO_AF GPIO_AF_UART4 + #define GPS_USART_IRQn UART4_IRQn + #define GPS_USART_IRQHandler UART4_IRQHandler + #define GPS_UART_GPIO GPIOA + #define GPS_TX_GPIO_PIN GPIO_Pin_0 // PA.00 + #define GPS_RX_GPIO_PIN GPIO_Pin_1 // PA.01 + #define GPS_TX_GPIO_PinSource GPIO_PinSource0 + #define GPS_RX_GPIO_PinSource GPIO_PinSource1 +#else + #define GPS_RCC_AHB1Periph 0 + #define GPS_RCC_APB1Periph 0 +#endif #endif // _HAL_H_ diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/horus/haptic_driver.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/horus/haptic_driver.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/horus/haptic_driver.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/horus/haptic_driver.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -22,7 +22,7 @@ void hapticOff(void) { - HAPTIC_GPIO_TIMER->CCR1 = 0; + HAPTIC_TIMER_COMPARE_VALUE = 0; } void hapticOn(uint32_t pwmPercent) @@ -30,7 +30,7 @@ if (pwmPercent > 100) { pwmPercent = 100; } - HAPTIC_GPIO_TIMER->CCR1 = pwmPercent; + HAPTIC_TIMER_COMPARE_VALUE = pwmPercent; } void hapticInit(void) @@ -47,10 +47,11 @@ HAPTIC_GPIO_TIMER->ARR = 100; HAPTIC_GPIO_TIMER->PSC = (PERI2_FREQUENCY * TIMER_MULT_APB2) / 10000 - 1; - HAPTIC_GPIO_TIMER->CCMR1 = TIM_CCMR1_OC1M_1 | TIM_CCMR1_OC1M_2; // PWM - HAPTIC_GPIO_TIMER->CCER = TIM_CCER_CC1E; + HAPTIC_GPIO_TIMER->CCMR1 = HAPTIC_TIMER_MODE; // PWM + HAPTIC_GPIO_TIMER->CCER = HAPTIC_TIMER_OUTPUT_ENABLE; + + hapticOff(); - HAPTIC_GPIO_TIMER->CCR1 = 0; HAPTIC_GPIO_TIMER->EGR = 0; HAPTIC_GPIO_TIMER->CR1 = TIM_CR1_CEN; // counter enable } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/horus/keys_driver.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/horus/keys_driver.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/horus/keys_driver.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/horus/keys_driver.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -129,7 +129,7 @@ case SW_S ## x ## 2: \ xxx = ~SWITCHES_GPIO_REG_ ## x & SWITCHES_GPIO_PIN_ ## x ; \ break -#define ADD_NEG_2POS_CASE(x) \ +#define ADD_INV_2POS_CASE(x) \ case SW_S ## x ## 2: \ xxx = SWITCHES_GPIO_REG_ ## x & SWITCHES_GPIO_PIN_ ## x ; \ break; \ @@ -152,6 +152,22 @@ xxx = xxx && (SWITCHES_GPIO_REG_ ## x ## _L & SWITCHES_GPIO_PIN_ ## x ## _L); \ } \ break +#define ADD_INV_3POS_CASE(x, i) \ + case SW_S ## x ## 2: \ + xxx = (SWITCHES_GPIO_REG_ ## x ## _H & SWITCHES_GPIO_PIN_ ## x ## _H); \ + if (IS_3POS(i)) { \ + xxx = xxx && (~SWITCHES_GPIO_REG_ ## x ## _L & SWITCHES_GPIO_PIN_ ## x ## _L); \ + } \ + break; \ + case SW_S ## x ## 1: \ + xxx = (SWITCHES_GPIO_REG_ ## x ## _H & SWITCHES_GPIO_PIN_ ## x ## _H) && (SWITCHES_GPIO_REG_ ## x ## _L & SWITCHES_GPIO_PIN_ ## x ## _L); \ + break; \ + case SW_S ## x ## 0: \ + xxx = (~SWITCHES_GPIO_REG_ ## x ## _H & SWITCHES_GPIO_PIN_ ## x ## _H); \ + if (IS_3POS(i)) { \ + xxx = xxx && (SWITCHES_GPIO_REG_ ## x ## _L & SWITCHES_GPIO_PIN_ ## x ## _L); \ + } \ + break #if !defined(BOOT) uint8_t keyState(uint8_t index) @@ -164,14 +180,25 @@ uint32_t xxx = 0; switch (index) { +#if defined(PCBX12S) ADD_3POS_CASE(A, 0); ADD_3POS_CASE(B, 1); ADD_3POS_CASE(C, 2); ADD_3POS_CASE(D, 3); ADD_3POS_CASE(E, 4); - ADD_NEG_2POS_CASE(F); + ADD_INV_2POS_CASE(F); + ADD_3POS_CASE(G, 6); + ADD_2POS_CASE(H); +#else + ADD_3POS_CASE(A, 0); + ADD_INV_3POS_CASE(B, 1); + ADD_3POS_CASE(C, 2); + ADD_INV_3POS_CASE(D, 3); + ADD_INV_3POS_CASE(E, 4); + ADD_2POS_CASE(F); ADD_3POS_CASE(G, 6); ADD_2POS_CASE(H); +#endif default: break; } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/horus/pulses_driver.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/horus/pulses_driver.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/horus/pulses_driver.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/horus/pulses_driver.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -96,17 +96,15 @@ } #endif -#if defined(MULTIMODULE) -void init_multimodule(uint32_t port) +void init_sbusOut(uint32_t port) { init_dsm2(port); } -void disable_multimodule(uint32_t port) +void disable_sbusOut(uint32_t port) { disable_dsm2(port); } -#endif void init_crossfire(uint32_t port) { diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/horus/pwm_driver.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/horus/pwm_driver.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/horus/pwm_driver.cpp 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/horus/pwm_driver.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -0,0 +1,198 @@ +/* + * Copyright (C) OpenTX + * + * Based on code named + * th9x - http://code.google.com/p/th9x + * er9x - http://code.google.com/p/er9x + * gruvin9x - http://code.google.com/p/gruvin9x + * + * License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + * + * 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. + */ + +#include "opentx.h" + +#define TIMESAMPLE_COUNT 6 + +uint8_t analogs_pwm_disabled = 0; +volatile uint32_t pwm_interrupt_count; +volatile uint8_t timer_capture_states[4]; +volatile uint32_t timer_capture_rising_time[4]; +volatile uint32_t timer_capture_values[4][TIMESAMPLE_COUNT]; +volatile uint8_t timer_capture_indexes[4]; + +void pwmInit() +{ + GPIO_InitTypeDef GPIO_InitStructure; + GPIO_InitStructure.GPIO_Pin = PWM_GPIOA_PINS; + GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF; + GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz; + GPIO_InitStructure.GPIO_OType = GPIO_OType_PP; + GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP; + GPIO_Init(PWM_GPIO, &GPIO_InitStructure); + + GPIO_PinAFConfig(PWM_GPIO, GPIO_PinSource0, PWM_GPIO_AF); + GPIO_PinAFConfig(PWM_GPIO, GPIO_PinSource1, PWM_GPIO_AF); + GPIO_PinAFConfig(PWM_GPIO, GPIO_PinSource2, PWM_GPIO_AF); + GPIO_PinAFConfig(PWM_GPIO, GPIO_PinSource3, PWM_GPIO_AF); + + PWM_TIMER->CR1 &= ~TIM_CR1_CEN; // Stop timer + PWM_TIMER->PSC = 80; + PWM_TIMER->ARR = 0xffff; + PWM_TIMER->CCMR1 = TIM_CCMR1_CC1S_0 | TIM_CCMR1_CC2S_0; + PWM_TIMER->CCMR2 = TIM_CCMR2_CC3S_0 | TIM_CCMR2_CC4S_0; + PWM_TIMER->CCER = TIM_CCER_CC1E | TIM_CCER_CC2E | TIM_CCER_CC3E | TIM_CCER_CC4E; + PWM_TIMER->DIER |= TIM_IT_CC1|TIM_IT_CC2|TIM_IT_CC3|TIM_IT_CC4; + PWM_TIMER->CR1 = TIM_CR1_CEN; // Start timer + + NVIC_EnableIRQ(PWM_IRQn); + NVIC_SetPriority(PWM_IRQn, 10); +} + +inline uint32_t TIM_GetCapture(uint8_t n) +{ + switch (n) { + case 0: + return PWM_TIMER->CCR1; + case 1: + return PWM_TIMER->CCR2; + case 2: + return PWM_TIMER->CCR3; + case 3: + return PWM_TIMER->CCR4; + default: + return 0; + } +} + +inline void TIM_SetPolarityRising(uint8_t n) +{ + switch (n) { + case 0: + PWM_TIMER->CCER &= ~TIM_CCER_CC1P; + break; + case 1: + PWM_TIMER->CCER &= ~TIM_CCER_CC2P; + break; + case 2: + PWM_TIMER->CCER &= ~TIM_CCER_CC3P; + break; + case 3: + PWM_TIMER->CCER &= ~TIM_CCER_CC4P; + break; + } +} + +inline void TIM_SetPolarityFalling(uint8_t n) +{ + switch (n) { + case 0: + PWM_TIMER->CCER |= TIM_CCER_CC1P; + break; + case 1: + PWM_TIMER->CCER |= TIM_CCER_CC2P; + break; + case 2: + PWM_TIMER->CCER |= TIM_CCER_CC3P; + break; + case 3: + PWM_TIMER->CCER |= TIM_CCER_CC4P; + break; + } +} + +inline void TIM_ClearITPendingBit(uint8_t n) +{ + switch (n) { + case 0: + PWM_TIMER->SR = ~TIM_IT_CC1; + break; + case 1: + PWM_TIMER->SR = ~TIM_IT_CC2; + break; + case 2: + PWM_TIMER->SR = ~TIM_IT_CC3; + break; + case 3: + PWM_TIMER->SR = ~TIM_IT_CC4; + break; + } +} + +inline uint32_t diff_with_16bits_overflow(uint32_t a, uint32_t b) +{ + if (b > a) + return b - a; + else + return b + 0xffff - a; +} + +extern "C" void PWM_IRQHandler(void) +{ + for (int i=0; i<4; i++) { + if (PWM_TIMER->SR & (TIM_DIER_CC1IE << i)) { + uint32_t capture = TIM_GetCapture(i); + if (timer_capture_states[i] != 0) { + uint32_t value = diff_with_16bits_overflow(timer_capture_rising_time[i], capture); + if (value < 10000) { + pwm_interrupt_count++; + timer_capture_values[i][timer_capture_indexes[i]++] = value; + timer_capture_indexes[i] %= TIMESAMPLE_COUNT; + } + TIM_SetPolarityRising(i); + timer_capture_states[i] = 0; + } + else { + timer_capture_rising_time[i] = capture; + TIM_SetPolarityFalling(i); + timer_capture_states[i] = 0x80; + } + TIM_ClearITPendingBit(i); + } + } +} + +void pwmRead(uint16_t * values) +{ + uint32_t tmp[4]; + + for (int i=0; i<4; i++) { + uint32_t mycount = 0; + uint32_t mymax = 0; + uint32_t mymin = 4095; + for (uint32_t j=0; j mymax) + mymax = value; + if (value < mymin) + mymin = value; + } + // from the 6 values, remove the min and max and divide by 4 + tmp[i] = (mycount - mymax - mymin) >> 2; + } + + values[0] = tmp[0]; + values[1] = tmp[1]; + values[2] = tmp[3]; + values[3] = tmp[2]; +} + +void pwmCheck() +{ + // I have ~1860 interrupts with only one stick + if (pwm_interrupt_count < 1000) { + analogs_pwm_disabled = true; +#if !defined(SIMU) + adcInit(); +#endif + } +} diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/horus/pwr_driver.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/horus/pwr_driver.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/horus/pwr_driver.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/horus/pwr_driver.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -70,7 +70,16 @@ void pwrOn() { + GPIO_InitTypeDef GPIO_InitStructure; + GPIO_InitStructure.GPIO_Pin = PWR_ON_GPIO_PIN; + GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT; + GPIO_InitStructure.GPIO_Speed = GPIO_Speed_2MHz; + GPIO_InitStructure.GPIO_OType = GPIO_OType_PP; + GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP; + GPIO_Init(PWR_GPIO, &GPIO_InitStructure); + GPIO_SetBits(PWR_GPIO, PWR_ON_GPIO_PIN); + shutdownRequest = NO_SHUTDOWN_REQUEST; shutdownReason = DIRTY_SHUTDOWN; } @@ -131,20 +140,16 @@ // powerupReason is there to cater for that, and is what is used in the firmware to decide whether we have to enter emergency mode. // This variable needs to be in a RAM section that is not initialized or zeroed, since once we exit this pwrResetHandler() function the // C runtime would otherwise overwrite it during program init. + // Only for X12, X10 power circuit causes inability to shut down on some samples. - if (shutdownRequest != SHUTDOWN_REQUEST) { - GPIO_InitTypeDef GPIO_InitStructure; - GPIO_InitStructure.GPIO_Pin = PWR_ON_GPIO_PIN; - GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT; - GPIO_InitStructure.GPIO_Speed = GPIO_Speed_2MHz; - GPIO_InitStructure.GPIO_OType = GPIO_OType_PP; - GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP; - GPIO_Init(PWR_GPIO, &GPIO_InitStructure); - +#if defined(PCBX12S) + if (shutdownRequest != SHUTDOWN_REQUEST || WAS_RESET_BY_WATCHDOG_OR_SOFTWARE()) { if (shutdownReason == DIRTY_SHUTDOWN) { powerupReason = DIRTY_SHUTDOWN; } - +#else + if (WAS_RESET_BY_WATCHDOG_OR_SOFTWARE()) { +#endif pwrOn(); } } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/mega2560/board.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/mega2560/board.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/mega2560/board.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/mega2560/board.h 2017-12-17 16:22:27.000000000 +0000 @@ -75,7 +75,7 @@ // Backlight driver #define backlightEnable() PORTC |= (1<PIO_PDSR, 1<<20) - SWITCH_CASE(1, PIOA->PIO_PDSR, 1<<15) - SWITCH_CASE(2, PIOC->PIO_PDSR, 1<<31) - SWITCH_3_CASE(3, PIOC->PIO_PDSR, PIOC->PIO_PDSR, 0x00004000, 0x00000800) + SWITCH_3_CASE(0, PIOC->PIO_PDSR, PIOC->PIO_PDSR, 0x00004000, 0x00000800) + SWITCH_CASE(1, PIOC->PIO_PDSR, 1<<20) + SWITCH_CASE(2, PIOA->PIO_PDSR, 1<<15) + SWITCH_CASE(3, PIOC->PIO_PDSR, 1<<31) SWITCH_CASE(4, PIOA->PIO_PDSR, 1<<2) SWITCH_CASE(5, PIOC->PIO_PDSR, 1<<16) SWITCH_CASE(6, PIOC->PIO_PDSR, 1<<8) #elif defined(PCBGRUVIN9X) - SWITCH_CASE(0, ping, 1<PWM_CH_NUM[3].PWM_CPDR; if (period == 3500 * 2) { @@ -341,7 +342,6 @@ sscptr->SSC_PTCR = SSC_PTCR_TXTEN; // Start transfers } break; -#endif default: pwmptr->PWM_CH_NUM[3].PWM_CPDRUPD = *modulePulsesData[EXTERNAL_MODULE].ppm.ptr++; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/sky9x/serial2_driver.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/sky9x/serial2_driver.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/sky9x/serial2_driver.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/sky9x/serial2_driver.cpp 2017-11-10 17:23:25.000000000 +0000 @@ -37,12 +37,12 @@ * This function is synchronous (i.e. uses polling). * c Character to send. */ -void serial2Putc(const char c) +void serial2Putc(const unsigned char c) { Uart *pUart = SECOND_SERIAL_UART; /* Wait for the transmitter to be ready */ - while ( (pUart->UART_SR & UART_SR_TXEMPTY) == 0 ) ; + while ( (pUart->UART_SR & UART_SR_TXRDY) == 0 ) ; /* Send character */ pUart->UART_THR = c; @@ -99,8 +99,12 @@ extern "C" void UART0_IRQHandler() { - serial2RxFifo.push(SECOND_SERIAL_UART->UART_RHR); + if ( SECOND_SERIAL_UART->UART_SR & UART_SR_RXRDY ) + { + serial2RxFifo.push(SECOND_SERIAL_UART->UART_RHR); + } } + #else #define SECOND_UART_Configure(...) #endif @@ -109,7 +113,6 @@ void serial2TelemetryInit(unsigned int /*protocol*/) { SECOND_UART_Configure(FRSKY_D_BAUDRATE, Master_frequency); - // startPdcUsartReceive(); } bool telemetrySecondPortReceive(uint8_t & data) @@ -117,3 +120,7 @@ return serial2RxFifo.pop(data); } #endif + +#if defined(DEBUG) && !defined(SIMU) +void serialPrintf(const char*, ... ) {} +#endif diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/taranis/bluetooth_driver.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/taranis/bluetooth_driver.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/taranis/bluetooth_driver.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/taranis/bluetooth_driver.cpp 1970-01-01 00:00:00.000000000 +0000 @@ -1,249 +0,0 @@ -/* - * Copyright (C) OpenTX - * - * Based on code named - * th9x - http://code.google.com/p/th9x - * er9x - http://code.google.com/p/er9x - * gruvin9x - http://code.google.com/p/gruvin9x - * - * License GPLv2: http://www.gnu.org/licenses/gpl-2.0.html - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License version 2 as - * published by the Free Software Foundation. - * - * 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. - */ - -#include "opentx.h" - -Fifo btTxFifo; -Fifo btRxFifo; - -enum BluetoothState -{ - BLUETOOTH_INIT, - BLUETOOTH_WAIT_TTM, - BLUETOOTH_WAIT_BAUDRATE_CHANGE, - BLUETOOTH_OK, -}; - -enum BluetoothWriteState -{ - BLUETOOTH_WRITE_IDLE, - BLUETOOTH_WRITE_INIT, - BLUETOOTH_WRITING, - BLUETOOTH_WRITE_DONE -}; - -volatile uint8_t bluetoothState = BLUETOOTH_INIT; -volatile uint8_t bluetoothWriteState = BLUETOOTH_WRITE_IDLE; - -void bluetoothInit(uint32_t baudrate) -{ - GPIO_InitTypeDef GPIO_InitStructure; - USART_InitTypeDef USART_InitStructure; - - USART_DeInit(BT_USART); - - RCC_AHB1PeriphClockCmd(BT_RCC_AHB1Periph, ENABLE); - RCC_APB2PeriphClockCmd(RCC_APB2Periph_USART6, ENABLE); - - GPIO_InitStructure.GPIO_Pin = BT_EN_GPIO_PIN; - GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT; - GPIO_InitStructure.GPIO_OType = GPIO_OType_PP; - GPIO_InitStructure.GPIO_Speed = GPIO_Speed_2MHz; - GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_NOPULL; - GPIO_Init(BT_EN_GPIO, &GPIO_InitStructure); - -#if defined(BT_BRTS_GPIO_PIN) - GPIO_InitStructure.GPIO_Pin = BT_BRTS_GPIO_PIN; - GPIO_Init(BT_BRTS_GPIO, &GPIO_InitStructure); - GPIO_SetBits(BT_BRTS_GPIO, BT_BRTS_GPIO_PIN); -#endif - -#if defined(BT_BCTS_GPIO_PIN) - GPIO_InitStructure.GPIO_Pin = BT_BCTS_GPIO_PIN; - GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN; - GPIO_Init(BT_BCTS_GPIO, &GPIO_InitStructure); -#endif - - GPIO_InitStructure.GPIO_Pin = BT_TX_GPIO_PIN|BT_RX_GPIO_PIN; - GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF; - GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP; - GPIO_Init(BT_GPIO_TXRX, &GPIO_InitStructure); - - GPIO_PinAFConfig(BT_GPIO_TXRX, BT_TX_GPIO_PinSource, BT_GPIO_AF); - GPIO_PinAFConfig(BT_GPIO_TXRX, BT_RX_GPIO_PinSource, BT_GPIO_AF); - - USART_DeInit(BT_USART); - USART_InitStructure.USART_BaudRate = baudrate; - USART_InitStructure.USART_Parity = USART_Parity_No; - USART_InitStructure.USART_StopBits = USART_StopBits_1; - USART_InitStructure.USART_WordLength = USART_WordLength_8b; - USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None; - USART_InitStructure.USART_Mode = USART_Mode_Rx | USART_Mode_Tx; - USART_Init(BT_USART, &USART_InitStructure); - - USART_Cmd(BT_USART, ENABLE); - USART_ITConfig(BT_USART, USART_IT_RXNE, ENABLE); - - NVIC_InitTypeDef NVIC_InitStructure; - NVIC_InitStructure.NVIC_IRQChannel = BT_USART_IRQn; - NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 8; - NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0; - NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; - NVIC_Init(&NVIC_InitStructure); - - GPIO_ResetBits(BT_EN_GPIO, BT_EN_GPIO_PIN); // open bluetooth -} - -void bluetoothDone() -{ - GPIO_SetBits(BT_EN_GPIO, BT_EN_GPIO_PIN); // close bluetooth -} - -extern "C" void USART6_IRQHandler(void) -{ - DEBUG_INTERRUPT(INT_BLUETOOTH); - if (USART_GetITStatus(BT_USART, USART_IT_RXNE) != RESET) { - USART_ClearITPendingBit(BT_USART, USART_IT_RXNE); - uint8_t byte = USART_ReceiveData(BT_USART); - btRxFifo.push(byte); - } - - if (USART_GetITStatus(BT_USART, USART_IT_TXE) != RESET) { - uint8_t byte; - bool result = btTxFifo.pop(byte); - if (result) { - USART_SendData(BT_USART, byte); - } - else { - USART_ITConfig(BT_USART, USART_IT_TXE, DISABLE); - bluetoothWriteState = BLUETOOTH_WRITE_DONE; - } - } -} - -void bluetoothWrite(const void * buffer, int len) -{ - uint8_t * data = (uint8_t *)buffer; - for (int i=0; i waitEnd) { - char ttm[] = "TTM:REN"; - int index = 0; - uint8_t c; - bool found = false; - while (btRxFifo.pop(c)) { - if (c == ttm[index]) { - index++; - if (index == sizeof(ttm)-1) { - found = true; - break; - } - } - else { - index = 0; - } - } - if (found) { - bluetoothState = BLUETOOTH_OK; - } - else { - bluetoothInit(BLUETOOTH_FACTORY_BAUDRATE); - const char btMessage[] = "TTM:BPS-115200"; - bluetoothWriteString(btMessage); - bluetoothState = BLUETOOTH_WAIT_BAUDRATE_CHANGE; - waitEnd = get_tmr10ms() + 250; // 2.5s - } - } - } - else if (bluetoothState == BLUETOOTH_WAIT_BAUDRATE_CHANGE) { - if (get_tmr10ms() > waitEnd) { - bluetoothState = BLUETOOTH_INIT; - } - } - } - - bluetoothWriteWakeup(); - } -} - -uint8_t bluetoothReady() -{ - return (bluetoothState == BLUETOOTH_OK); -} - -int bluetoothRead(void * buffer, int len) -{ - int result = 0; - uint8_t * data = (uint8_t *)buffer; - while (result < len) { - uint8_t byte; - if (!btRxFifo.pop(byte)) { - break; - } - data[result++] = byte; - } - return result; -} diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/taranis/board.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/taranis/board.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/taranis/board.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/taranis/board.cpp 2017-11-10 17:23:25.000000000 +0000 @@ -82,6 +82,7 @@ if (++pre_scale >= 2) { pre_scale = 0 ; DEBUG_TIMER_START(debugTimerPer10ms); + DEBUG_TIMER_SAMPLE(debugTimerPer10msPeriod); per10ms(); DEBUG_TIMER_STOP(debugTimerPer10ms); } @@ -100,10 +101,11 @@ } #endif -#if defined(PCBX9E) && !defined(SIMU) -#define PWR_PRESS_DURATION_MIN 200 // 2s +#if (defined(PCBX9E) || defined(PCBX7)) && !defined(SIMU) +#define PWR_PRESS_DURATION_MIN 100 // 1s #define PWR_PRESS_DURATION_MAX 500 // 5s - +#endif +#if (defined(PCBX9E) && !defined(SIMU)) const pm_uchar bmp_startup[] PROGMEM = { #include "startup.lbm" }; @@ -145,9 +147,9 @@ void boardInit() { #if !defined(SIMU) - RCC_AHB1PeriphClockCmd(PWR_RCC_AHB1Periph | PCBREV_RCC_AHB1Periph | KEYS_RCC_AHB1Periph | LCD_RCC_AHB1Periph | AUDIO_RCC_AHB1Periph | BACKLIGHT_RCC_AHB1Periph | ADC_RCC_AHB1Periph | I2C_RCC_AHB1Periph | SD_RCC_AHB1Periph | HAPTIC_RCC_AHB1Periph | INTMODULE_RCC_AHB1Periph | EXTMODULE_RCC_AHB1Periph | TELEMETRY_RCC_AHB1Periph | SPORT_UPDATE_RCC_AHB1Periph | SERIAL_RCC_AHB1Periph | TRAINER_RCC_AHB1Periph | HEARTBEAT_RCC_AHB1Periph, ENABLE); - RCC_APB1PeriphClockCmd(LCD_RCC_APB1Periph | AUDIO_RCC_APB1Periph | BACKLIGHT_RCC_APB1Periph | INTERRUPT_5MS_APB1Periph | TIMER_2MHz_APB1Periph | I2C_RCC_APB1Periph | SD_RCC_APB1Periph | TRAINER_RCC_APB1Periph | TELEMETRY_RCC_APB1Periph | SERIAL_RCC_APB1Periph, ENABLE); - RCC_APB2PeriphClockCmd(BACKLIGHT_RCC_APB2Periph | ADC_RCC_APB2Periph | HAPTIC_RCC_APB2Periph | INTMODULE_RCC_APB2Periph | EXTMODULE_RCC_APB2Periph | HEARTBEAT_RCC_APB2Periph, ENABLE); + RCC_AHB1PeriphClockCmd(PWR_RCC_AHB1Periph | PCBREV_RCC_AHB1Periph | KEYS_RCC_AHB1Periph | LCD_RCC_AHB1Periph | AUDIO_RCC_AHB1Periph | BACKLIGHT_RCC_AHB1Periph | ADC_RCC_AHB1Periph | I2C_RCC_AHB1Periph | SD_RCC_AHB1Periph | HAPTIC_RCC_AHB1Periph | INTMODULE_RCC_AHB1Periph | EXTMODULE_RCC_AHB1Periph | TELEMETRY_RCC_AHB1Periph | SPORT_UPDATE_RCC_AHB1Periph | SERIAL_RCC_AHB1Periph | TRAINER_RCC_AHB1Periph | HEARTBEAT_RCC_AHB1Periph | BT_RCC_AHB1Periph, ENABLE); + RCC_APB1PeriphClockCmd(LCD_RCC_APB1Periph | AUDIO_RCC_APB1Periph | BACKLIGHT_RCC_APB1Periph | INTERRUPT_5MS_APB1Periph | TIMER_2MHz_APB1Periph | I2C_RCC_APB1Periph | SD_RCC_APB1Periph | TRAINER_RCC_APB1Periph | TELEMETRY_RCC_APB1Periph | SERIAL_RCC_APB1Periph | BT_RCC_APB1Periph, ENABLE); + RCC_APB2PeriphClockCmd(BACKLIGHT_RCC_APB2Periph | ADC_RCC_APB2Periph | HAPTIC_RCC_APB2Periph | INTMODULE_RCC_APB2Periph | EXTMODULE_RCC_APB2Periph | HEARTBEAT_RCC_APB2Periph | BT_RCC_APB2Periph, ENABLE); #if !defined(PCBX9E) // some X9E boards need that the pwrInit() is moved a little bit later @@ -179,7 +181,7 @@ hapticInit(); #endif -#if defined(PCBX9E) || defined(PCBX7) +#if defined(BLUETOOTH) bluetoothInit(BLUETOOTH_DEFAULT_BAUDRATE); #endif @@ -187,10 +189,14 @@ DBGMCU_APB1PeriphConfig(DBGMCU_IWDG_STOP|DBGMCU_TIM1_STOP|DBGMCU_TIM2_STOP|DBGMCU_TIM3_STOP|DBGMCU_TIM6_STOP|DBGMCU_TIM8_STOP|DBGMCU_TIM10_STOP|DBGMCU_TIM13_STOP|DBGMCU_TIM14_STOP, ENABLE); #endif -#if defined(PCBX9E) +#if defined(PCBX9E) || defined(PCBX7) if (!WAS_RESET_BY_WATCHDOG_OR_SOFTWARE()) { lcdClear(); +#if defined(PCBX9E) lcdDrawBitmap(76, 2, bmp_lock, 0, 60); +#else + lcdDrawFilledRect(LCD_W / 2 - 18, LCD_H / 2 - 3, 6, 6, SOLID, 0); +#endif lcdRefresh(); lcdRefreshWait(); @@ -202,7 +208,15 @@ if (duration < PWR_PRESS_DURATION_MIN) { unsigned index = duration / (PWR_PRESS_DURATION_MIN / 4); lcdClear(); +#if defined(PCBX9E) lcdDrawBitmap(76, 2, bmp_startup, index*60, 60); +#else + for(uint8_t i= 0; i < 4; i++) { + if (index >= i) { + lcdDrawFilledRect(LCD_W / 2 - 18 + 10 * i, LCD_H / 2 - 3, 6, 6, SOLID, 0); + } + } +#endif } else if (duration >= PWR_PRESS_DURATION_MAX) { drawSleepBitmap(); @@ -227,7 +241,9 @@ pwrInit(); backlightInit(); } +#if defined(PCBX9E) toplcdInit(); +#endif #else backlightInit(); #endif @@ -283,7 +299,7 @@ case TRAINER_MODE_MASTER_SBUS_EXTERNAL_MODULE: stop_sbus_on_heartbeat_capture() ; break; -#if defined(SERIAL2) +#if !defined(PCBX7) && !defined(PCBX9E) case TRAINER_MODE_MASTER_BATTERY_COMPARTMENT: serial2Stop(); #endif @@ -300,7 +316,7 @@ case TRAINER_MODE_MASTER_SBUS_EXTERNAL_MODULE: init_sbus_on_heartbeat_capture() ; break; -#if defined(SERIAL2) +#if !defined(PCBX7) && !defined(PCBX9E) case TRAINER_MODE_MASTER_BATTERY_COMPARTMENT: if (g_eeGeneral.serial2Mode == UART_MODE_SBUS_TRAINER) { serial2SbusInit(); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/taranis/board.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/taranis/board.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/taranis/board.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/taranis/board.h 2017-10-31 16:16:43.000000000 +0000 @@ -22,6 +22,7 @@ #define _BOARD_H_ #include "stddef.h" +#include "stdbool.h" #if defined(__cplusplus) && !defined(SIMU) extern "C" { @@ -71,6 +72,7 @@ #pragma clang diagnostic pop #endif +#include "usb_driver.h" #if !defined(SIMU) #include "usbd_cdc_core.h" #include "usbd_msc_core.h" @@ -157,13 +159,14 @@ #define sdInit() #define sdMount() #define sdDone() +#define SD_CARD_PRESENT() true #else void sdInit(void); void sdMount(void); void sdDone(void); void sdPoll10ms(void); uint32_t sdMounted(void); -#define SD_CARD_PRESENT() (~SD_GPIO_PRESENT->IDR & SD_GPIO_PIN_PRESENT) +#define SD_CARD_PRESENT() ((SD_GPIO_PRESENT->IDR & SD_GPIO_PIN_PRESENT)==0) #endif // Flash Write driver @@ -191,11 +194,8 @@ void disable_dsm2( uint32_t module_index ); void init_crossfire( uint32_t module_index ); void disable_crossfire( uint32_t module_index ); - -#if defined(MULTIMODULE) -void init_multimodule(uint32_t module_index); -void disable_multimodule(uint32_t module_index); -#endif +void init_sbusOut(uint32_t module_index); +void disable_sbusOut(uint32_t module_index); // Trainer driver void init_trainer_ppm(void); @@ -453,14 +453,7 @@ #define BACKLIGHT_ENABLE() backlightEnable(g_eeGeneral.backlightBright) #endif -// USB driver -int usbPlugged(); -void usbInit(); -void usbStart(); -void usbStop(); -uint8_t usbStarted(); -void usbSerialPutc(uint8_t c); -#if defined(USB_JOYSTICK) && !defined(SIMU) +#if !defined(SIMU) void usbJoystickUpdate(); #endif #define USB_NAME "FrSky Taranis" @@ -549,13 +542,14 @@ // BT driver #define BLUETOOTH_DEFAULT_BAUDRATE 115200 +#if defined(PCBX9E) && !defined(USEHORUSBT) #define BLUETOOTH_FACTORY_BAUDRATE 9600 -uint8_t bluetoothReady(void); +#else +#define BLUETOOTH_FACTORY_BAUDRATE 57600 +#endif void bluetoothInit(uint32_t baudrate); -void bluetoothWrite(const void * buffer, int len); -void bluetoothWriteString(const char * str); -int bluetoothRead(void * buffer, int len); -void bluetoothWakeup(void); +void bluetoothWriteWakeup(void); +uint8_t bluetoothIsWriting(void); void bluetoothDone(void); // LED driver diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/taranis/bootloader/CMakeLists.txt opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/taranis/bootloader/CMakeLists.txt --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/taranis/bootloader/CMakeLists.txt 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/taranis/bootloader/CMakeLists.txt 2017-12-17 16:22:27.000000000 +0000 @@ -61,8 +61,8 @@ boot.cpp ) -remove_definitions(-DUSB_JOYSTICK -DUSB_SERIAL -DLUA -DDEBUG) -add_definitions(-DBOOT -DUSB_MASS_STORAGE) +remove_definitions(-DLUA -DDEBUG) +add_definitions(-DBOOT) set(CMAKE_EXE_LINKER_FLAGS "-mcpu=${MCU} -mthumb -nostartfiles -lm -T${RADIO_SRC_DIRECTORY}/targets/taranis/stm32_ramboot.ld -Wl,-Map=bootloader.map,--cref,--no-warn-mismatch,--gc-sections") diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/taranis/CMakeLists.txt opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/taranis/CMakeLists.txt --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/taranis/CMakeLists.txt 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/taranis/CMakeLists.txt 2017-11-20 18:44:06.000000000 +0000 @@ -11,14 +11,12 @@ set(HAPTIC YES) set(LUA_EXPORT lua_export_x9e) set(FLAVOUR x9e) - add_definitions(-DSTM32F40_41xxx -DPCBX9E) + add_definitions(-DSTM32F40_41xxx -DPCBX9E -DPCBX9) add_definitions(-DEEPROM_VARIANT=0x8000) - add_definitions(-DBLUETOOTH) add_definitions(-DPWR_BUTTON_${PWR_BUTTON}) set(FIRMWARE_TARGET_SRC ${FIRMWARE_TARGET_SRC} top_lcd_driver.cpp - bluetooth_driver.cpp startup_stm32f40_41xxx.s ) set(SERIAL2_DRIVER ../common/arm/stm32/serial2_driver.cpp) @@ -26,7 +24,6 @@ add_definitions(-DHORUS_STICKS) endif() set(GUI_DIR 212x64) - set(GUI_SRC ${GUI_SRC} bmp.cpp) set(BITMAPS_TARGET taranis_bitmaps) set(LCD_DRIVER lcd_driver_spi.cpp) set(GVAR_SCREEN model_gvars.cpp) @@ -37,10 +34,9 @@ set(HAPTIC YES) set(LUA_EXPORT lua_export_x9d) set(FLAVOUR x9d+) - add_definitions(-DPCBX9DP) + add_definitions(-DPCBX9DP -DPCBX9) add_definitions(-DEEPROM_VARIANT=0) set(GUI_DIR 212x64) - set(GUI_SRC ${GUI_SRC} bmp.cpp) set(BITMAPS_TARGET taranis_bitmaps) set(LCD_DRIVER lcd_driver_spi.cpp) set(SERIAL2_DRIVER ../common/arm/stm32/serial2_driver.cpp) @@ -52,10 +48,9 @@ option(HAPTIC "Haptic support" OFF) set(LUA_EXPORT lua_export_x9d) set(FLAVOUR x9d) - add_definitions(-DPCBX9D) + add_definitions(-DPCBX9D -DPCBX9) add_definitions(-DEEPROM_VARIANT=0) set(GUI_DIR 212x64) - set(GUI_SRC ${GUI_SRC} bmp.cpp) set(BITMAPS_TARGET taranis_bitmaps) set(LCD_DRIVER lcd_driver_aspi.cpp) set(SERIAL2_DRIVER ../common/arm/stm32/serial2_driver.cpp) @@ -71,15 +66,23 @@ add_definitions(-DPCBX7 -DSOFTWARE_VOLUME) add_definitions(-DEEPROM_VARIANT=0x4000) add_definitions(-DPWR_BUTTON_${PWR_BUTTON}) - set(FIRMWARE_TARGET_SRC - ${FIRMWARE_TARGET_SRC} - bluetooth_driver.cpp - ) set(GUI_DIR 128x64) set(BITMAPS_TARGET 9x_bitmaps) set(LCD_DRIVER lcd_driver_spi.cpp) endif() +if(PCB STREQUAL X9E OR PCB STREQUAL X7) + add_definitions(-DBLUETOOTH) + set(TARGET_SRC + ${TARGET_SRC} + ../common/arm/stm32/bluetooth_driver.cpp + ) + set(SRC + ${SRC} + bluetooth.cpp + ) +endif() + set(HSE_VALUE 12000000) set(SDCARD YES) set(EEPROM EEPROM_RLC) @@ -103,6 +106,7 @@ view_channels.cpp view_telemetry.cpp view_about.cpp + bmp.cpp ../screenshot.cpp ) diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/taranis/diskio.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/taranis/diskio.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/taranis/diskio.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/taranis/diskio.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -993,13 +993,18 @@ void sdInit(void) { TRACE("sdInit"); - + ioMutex = CoCreateMutex(); - if (ioMutex >= CFG_MAX_MUTEX ) { + if (ioMutex >= CFG_MAX_MUTEX) { //sd error return; } + sdMount(); +} +void sdMount() +{ + TRACE("sdMount"); if (f_mount(&g_FATFS_Obj, "", 1) == FR_OK) { // call sdGetFreeSectors() now because f_getfree() takes a long time first time it's called sdGetFreeSectors(); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/taranis/extmodule_driver.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/taranis/extmodule_driver.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/taranis/extmodule_driver.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/taranis/extmodule_driver.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -117,7 +117,7 @@ EXTMODULE_TIMER->CR1 &= ~TIM_CR1_CEN; EXTMODULE_TIMER->PSC = EXTMODULE_TIMER_FREQ / 2000000 - 1; // 0.5uS (2Mhz) EXTMODULE_TIMER->ARR = 18000; - EXTMODULE_TIMER->CCER = TIM_CCER_CC1E | TIM_CCER_CC1NE; + EXTMODULE_TIMER->CCER = TIM_CCER_CC1E | TIM_CCER_CC1NE; //polarity, default low EXTMODULE_TIMER->BDTR = TIM_BDTR_MOE; // Enable outputs EXTMODULE_TIMER->CCR1 = 18; EXTMODULE_TIMER->CCMR1 = TIM_CCMR1_OC1M_2 | TIM_CCMR1_OC1M_0; // Force O/P high @@ -220,7 +220,9 @@ EXTMODULE_DMA_STREAM->NDTR = modulePulsesData[EXTERNAL_MODULE].pxx.ptr - modulePulsesData[EXTERNAL_MODULE].pxx.pulses; EXTMODULE_DMA_STREAM->CR |= DMA_SxCR_EN | DMA_SxCR_TCIE; // Enable DMA } - else if (IS_DSM2_PROTOCOL(s_current_protocol[EXTERNAL_MODULE]) || IS_MULTIMODULE_PROTOCOL(s_current_protocol[EXTERNAL_MODULE])) { + else if (IS_DSM2_PROTOCOL(s_current_protocol[EXTERNAL_MODULE]) || IS_MULTIMODULE_PROTOCOL(s_current_protocol[EXTERNAL_MODULE]) || IS_SBUS_PROTOCOL(s_current_protocol[EXTERNAL_MODULE])) { + if (IS_SBUS_PROTOCOL(s_current_protocol[EXTERNAL_MODULE])) + EXTMODULE_TIMER->CCER = TIM_CCER_CC1NE | (GET_SBUS_POLARITY(EXTERNAL_MODULE) ? TIM_CCER_CC1NP : 0); // reverse polarity for Sbus if needed EXTMODULE_TIMER->CCR2 = *(modulePulsesData[EXTERNAL_MODULE].dsm2.ptr - 1) - 4000; // 2mS in advance EXTMODULE_DMA_STREAM->CR &= ~DMA_SxCR_EN; // Disable DMA EXTMODULE_DMA_STREAM->CR |= EXTMODULE_DMA_CHANNEL | DMA_SxCR_DIR_0 | DMA_SxCR_MINC | DMA_SxCR_PSIZE_0 | DMA_SxCR_MSIZE_0 | DMA_SxCR_PL_0 | DMA_SxCR_PL_1; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/taranis/hal.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/taranis/hal.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/taranis/hal.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/taranis/hal.h 2017-12-17 16:22:27.000000000 +0000 @@ -657,7 +657,7 @@ #define LCD_RST_GPIO GPIOD #define LCD_RST_GPIO_PIN GPIO_Pin_15 // PD.15 #define LCD_DMA DMA1 - #define LDC_DMA_Stream DMA1_Stream7 + #define LCD_DMA_Stream DMA1_Stream7 #define LCD_DMA_Stream_IRQn DMA1_Stream7_IRQn #define LCD_DMA_Stream_IRQHandler DMA1_Stream7_IRQHandler #define LCD_DMA_FLAGS (DMA_HIFCR_CTCIF7 | DMA_HIFCR_CHTIF7 | DMA_HIFCR_CTEIF7 | DMA_HIFCR_CDMEIF7 | DMA_HIFCR_CFEIF7) @@ -678,7 +678,7 @@ #define LCD_RST_GPIO GPIOD #define LCD_RST_GPIO_PIN GPIO_Pin_12 // PD.12 #define LCD_DMA DMA1 - #define LDC_DMA_Stream DMA1_Stream7 + #define LCD_DMA_Stream DMA1_Stream7 #define LCD_DMA_Stream_IRQn DMA1_Stream7_IRQn #define LCD_DMA_Stream_IRQHandler DMA1_Stream7_IRQHandler #define LCD_DMA_FLAGS (DMA_HIFCR_CTCIF7 | DMA_HIFCR_CHTIF7 | DMA_HIFCR_CTEIF7 | DMA_HIFCR_CDMEIF7 | DMA_HIFCR_CFEIF7) @@ -790,7 +790,9 @@ #define BT_USART USART6 #define BT_GPIO_AF GPIO_AF_USART6 #define BT_USART_IRQn USART6_IRQn - #define BT_RCC_AHB1Periph (RCC_AHB1Periph_GPIOG | RCC_AHB1Periph_GPIOD | RCC_AHB1Periph_GPIOB) + #define BT_RCC_AHB1Periph (RCC_AHB1Periph_GPIOD | RCC_AHB1Periph_GPIOE | RCC_AHB1Periph_GPIOG) + #define BT_RCC_APB1Periph 0 + #define BT_RCC_APB2Periph RCC_APB2Periph_USART6 #define BT_GPIO_TXRX GPIOG #define BT_TX_GPIO_PIN GPIO_Pin_14 // PG.14 #define BT_RX_GPIO_PIN GPIO_Pin_9 // PG.09 @@ -802,9 +804,11 @@ #define BT_BCTS_GPIO_PIN GPIO_Pin_6 // PG.06 #define BT_TX_GPIO_PinSource GPIO_PinSource14 #define BT_RX_GPIO_PinSource GPIO_PinSource9 + #define BT_USART_IRQHandler USART6_IRQHandler #elif defined(PCBX7) #define BT_RCC_AHB1Periph (RCC_AHB1Periph_GPIOB | RCC_AHB1Periph_GPIOE | RCC_AHB1Periph_DMA1) #define BT_RCC_APB1Periph RCC_APB1Periph_USART3 + #define BT_RCC_APB2Periph 0 #define BT_EN_GPIO GPIOE #define BT_EN_GPIO_PIN GPIO_Pin_12 // PE.12 #define BT_GPIO_TXRX GPIOB @@ -818,6 +822,10 @@ #define BT_USART_IRQn USART3_IRQn #define BT_DMA_Stream_RX DMA1_Stream1 #define BT_DMA_Channel_RX DMA_Channel_4 +#else + #define BT_RCC_AHB1Periph 0 + #define BT_RCC_APB1Periph 0 + #define BT_RCC_APB2Periph 0 #endif // 5ms Interrupt diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/taranis/haptic_driver.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/taranis/haptic_driver.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/taranis/haptic_driver.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/taranis/haptic_driver.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -46,14 +46,14 @@ GPIO_PinAFConfig(HAPTIC_GPIO, HAPTIC_GPIO_PinSource, HAPTIC_GPIO_AF); - HAPTIC_TIMER->ARR = 100 ; + HAPTIC_TIMER->ARR = 100; HAPTIC_TIMER->PSC = (PERI2_FREQUENCY * TIMER_MULT_APB2) / 10000 - 1; - HAPTIC_TIMER->CCMR1 = TIM_CCMR1_OC1M_1 | TIM_CCMR1_OC1M_2 ; // PWM - HAPTIC_TIMER->CCER = TIM_CCER_CC1E ; + HAPTIC_TIMER->CCMR1 = TIM_CCMR1_OC1M_1 | TIM_CCMR1_OC1M_2; // PWM + HAPTIC_TIMER->CCER = TIM_CCER_CC1E; - HAPTIC_TIMER->CCR1 = 0 ; - HAPTIC_TIMER->EGR = 0 ; - HAPTIC_TIMER->CR1 = TIM_CR1_CEN ; // Counter enable + HAPTIC_TIMER->CCR1 = 0; + HAPTIC_TIMER->EGR = 0; + HAPTIC_TIMER->CR1 = TIM_CR1_CEN; // Counter enable } #else diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/taranis/lcd_driver_spi.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/taranis/lcd_driver_spi.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/taranis/lcd_driver_spi.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/taranis/lcd_driver_spi.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -85,17 +85,17 @@ GPIO_PinAFConfig(LCD_SPI_GPIO, LCD_MOSI_GPIO_PinSource, LCD_GPIO_AF); GPIO_PinAFConfig(LCD_SPI_GPIO, LCD_CLK_GPIO_PinSource, LCD_GPIO_AF); - LDC_DMA_Stream->CR &= ~DMA_SxCR_EN; // Disable DMA + LCD_DMA_Stream->CR &= ~DMA_SxCR_EN; // Disable DMA LCD_DMA->HIFCR = LCD_DMA_FLAGS; // Write ones to clear bits - LDC_DMA_Stream->CR = DMA_SxCR_PL_0 | DMA_SxCR_MINC | DMA_SxCR_DIR_0; - LDC_DMA_Stream->PAR = (uint32_t)&LCD_SPI->DR; + LCD_DMA_Stream->CR = DMA_SxCR_PL_0 | DMA_SxCR_MINC | DMA_SxCR_DIR_0; + LCD_DMA_Stream->PAR = (uint32_t)&LCD_SPI->DR; #if defined(PCBX7) - LDC_DMA_Stream->NDTR = LCD_W; + LCD_DMA_Stream->NDTR = LCD_W; #else - LDC_DMA_Stream->M0AR = (uint32_t)displayBuf; - LDC_DMA_Stream->NDTR = LCD_W*LCD_H/8*4; + LCD_DMA_Stream->M0AR = (uint32_t)displayBuf; + LCD_DMA_Stream->NDTR = LCD_W*LCD_H/8*4; #endif - LDC_DMA_Stream->FCR = 0x05; // DMA_SxFCR_DMDIS | DMA_SxFCR_FTH_0; + LCD_DMA_Stream->FCR = 0x05; // DMA_SxFCR_DMDIS | DMA_SxFCR_FTH_0; NVIC_EnableIRQ(LCD_DMA_Stream_IRQn); } @@ -187,10 +187,10 @@ LCD_A0_HIGH(); lcd_busy = true; - LDC_DMA_Stream->CR &= ~DMA_SxCR_EN; // Disable DMA + LCD_DMA_Stream->CR &= ~DMA_SxCR_EN; // Disable DMA LCD_DMA->HIFCR = LCD_DMA_FLAGS; // Write ones to clear bits - LDC_DMA_Stream->M0AR = (uint32_t)p; - LDC_DMA_Stream->CR |= DMA_SxCR_EN | DMA_SxCR_TCIE; // Enable DMA & TC interrupts + LCD_DMA_Stream->M0AR = (uint32_t)p; + LCD_DMA_Stream->CR |= DMA_SxCR_EN | DMA_SxCR_TCIE; // Enable DMA & TC interrupts LCD_SPI->CR2 |= SPI_CR2_TXDMAEN; WAIT_FOR_DMA_END(); @@ -208,16 +208,16 @@ LCD_NCS_LOW(); LCD_A0_HIGH(); - LDC_DMA_Stream->CR &= ~DMA_SxCR_EN; // Disable DMA + LCD_DMA_Stream->CR &= ~DMA_SxCR_EN; // Disable DMA LCD_DMA->HIFCR = LCD_DMA_FLAGS; // Write ones to clear bits #if defined(LCD_DUAL_BUFFER) // Switch LCD buffer - LDC_DMA_Stream->M0AR = (uint32_t)displayBuf; + LCD_DMA_Stream->M0AR = (uint32_t)displayBuf; displayBuf = (displayBuf == displayBuf1) ? displayBuf2 : displayBuf1; #endif - LDC_DMA_Stream->CR |= DMA_SxCR_EN | DMA_SxCR_TCIE; // Enable DMA & TC interrupts + LCD_DMA_Stream->CR |= DMA_SxCR_EN | DMA_SxCR_TCIE; // Enable DMA & TC interrupts LCD_SPI->CR2 |= SPI_CR2_TXDMAEN; #endif } @@ -226,10 +226,10 @@ { DEBUG_INTERRUPT(INT_LCD); - LDC_DMA_Stream->CR &= ~DMA_SxCR_TCIE; // Stop interrupt + LCD_DMA_Stream->CR &= ~DMA_SxCR_TCIE; // Stop interrupt LCD_DMA->HIFCR |= LCD_DMA_FLAG_INT; // Clear interrupt flag LCD_SPI->CR2 &= ~SPI_CR2_TXDMAEN; - LDC_DMA_Stream->CR &= ~DMA_SxCR_EN; // Disable DMA + LCD_DMA_Stream->CR &= ~DMA_SxCR_EN; // Disable DMA while (LCD_SPI->SR & SPI_SR_BSY) { /* Wait for SPI to finish sending data diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/taranis/pulses_driver.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/taranis/pulses_driver.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/taranis/pulses_driver.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/taranis/pulses_driver.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -71,17 +71,15 @@ } #endif -#if defined(MULTIMODULE) -void init_multimodule(uint32_t port) +void init_sbusOut(uint32_t port) { init_dsm2(port); } -void disable_multimodule(uint32_t port) +void disable_sbusOut(uint32_t port) { disable_dsm2(port); } -#endif void init_ppm(uint32_t port) diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/taranis/telemetry_driver.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/taranis/telemetry_driver.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/taranis/telemetry_driver.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/taranis/telemetry_driver.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -114,6 +114,7 @@ DMA_Cmd(TELEMETRY_DMA_Stream_TX, ENABLE); USART_DMACmd(TELEMETRY_USART, USART_DMAReq_Tx, ENABLE); DMA_ITConfig(TELEMETRY_DMA_Stream_TX, DMA_IT_TC, ENABLE); + USART_ClearITPendingBit(TELEMETRY_USART, USART_IT_TC); // enable interrupt and set it's priority NVIC_EnableIRQ(TELEMETRY_DMA_TX_Stream_IRQ) ; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/taranis/trainer_driver.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/taranis/trainer_driver.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/targets/taranis/trainer_driver.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/targets/taranis/trainer_driver.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -193,7 +193,7 @@ TRAINER_TIMER->CR1 &= ~TIM_CR1_CEN; // Stop counter NVIC_DisableIRQ(TRAINER_TIMER_IRQn); // Stop Interrupt - if (!IS_EXTERNAL_MODULE_PRESENT()) { + if (!IS_EXTERNAL_MODULE_ENABLED()) { EXTERNAL_MODULE_OFF(); } } @@ -255,7 +255,7 @@ DMA_DeInit(HEARTBEAT_DMA_Stream); NVIC_DisableIRQ(HEARTBEAT_USART_IRQn); - if (!IS_EXTERNAL_MODULE_PRESENT()) { + if (!IS_EXTERNAL_MODULE_ENABLED()) { EXTERNAL_MODULE_OFF(); } } @@ -265,7 +265,7 @@ switch (currentTrainerMode) { case TRAINER_MODE_MASTER_SBUS_EXTERNAL_MODULE: return heartbeatFifo.pop(*byte); -#if defined(SERIAL2) +#if !defined(PCBX7) && !defined(PCBX9E) case TRAINER_MODE_MASTER_BATTERY_COMPARTMENT: return serial2RxFifo.pop(*byte); #endif diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/tasks_arm.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/tasks_arm.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/tasks_arm.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/tasks_arm.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -30,11 +30,6 @@ OS_TID audioTaskId; TaskStack audioStack; -#if defined(BLUETOOTH) -OS_TID btTaskId; -TaskStack bluetoothStack; -#endif - OS_MutexID audioMutex; OS_MutexID mixerMutex; @@ -93,11 +88,6 @@ volatile uint16_t timeForcePowerOffPressed = 0; -void resetForcePowerOffRequest() -{ - timeForcePowerOffPressed = 0; -} - bool isForcePowerOffRequested() { if (pwrOffPressed()) { @@ -143,7 +133,7 @@ uint32_t now = CoGetOSTime(); bool run = false; -#if defined(USB_JOYSTICK) && !defined(SIMU) +#if !defined(SIMU) && defined(STM32) if ((now - lastRunTime) >= (usbStarted() ? 5 : 10)) { // run at least every 20ms (every 10ms if USB is active) #else if ((now - lastRunTime) >= 10) { // run at least every 20ms @@ -175,8 +165,10 @@ CoLeaveMutexSection(mixerMutex); DEBUG_TIMER_STOP(debugTimerMixer); -#if defined(USB_JOYSTICK) && !defined(SIMU) - usbJoystickUpdate(); +#if defined(STM32) && !defined(SIMU) + if (getSelectedUsbMode() == USB_JOYSTICK_MODE) { + usbJoystickUpdate(); + } #endif #if defined(TELEMETRY_FRSKY) || defined(TELEMETRY_MAVLINK) @@ -185,6 +177,10 @@ DEBUG_TIMER_STOP(debugTimerTelemetryWakeup); #endif +#if defined(BLUETOOTH) + bluetoothWakeup(); +#endif + if (heartbeat == HEART_WDT_CHECK) { wdt_reset(); heartbeat = 0; @@ -266,8 +262,6 @@ boardOff(); // Only turn power off if necessary } -extern void audioTask(void* pdata); - void tasksStart() { CoInitOS(); @@ -276,16 +270,14 @@ cliStart(); #endif -#if defined(BLUETOOTH) && defined(PCBSKY9X) - btTaskId = CoCreateTask(btTask, NULL, 15, &bluetoothStack.stack[BLUETOOTH_STACK_SIZE-1], BLUETOOTH_STACK_SIZE); -#endif - mixerTaskId = CoCreateTask(mixerTask, NULL, 5, &mixerStack.stack[MIXER_STACK_SIZE-1], MIXER_STACK_SIZE); menusTaskId = CoCreateTask(menusTask, NULL, 10, &menusStack.stack[MENUS_STACK_SIZE-1], MENUS_STACK_SIZE); + #if !defined(SIMU) // TODO move the SIMU audio in this task audioTaskId = CoCreateTask(audioTask, NULL, 7, &audioStack.stack[AUDIO_STACK_SIZE-1], AUDIO_STACK_SIZE); #endif + audioMutex = CoCreateMutex(); mixerMutex = CoCreateMutex(); diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/tasks_arm.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/tasks_arm.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/tasks_arm.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/tasks_arm.h 2017-12-17 16:22:27.000000000 +0000 @@ -71,11 +71,9 @@ extern OS_TID audioTaskId; extern TaskStack audioStack; -#if defined(BLUETOOTH) -extern OS_TID btTaskId; -extern TaskStack bluetoothStack; -#endif - void tasksStart(); +extern volatile uint16_t timeForcePowerOffPressed; +inline void resetForcePowerOffRequest() {timeForcePowerOffPressed = 0; } + #endif // _TASKS_ARM_H_ diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/telemetry/crossfire.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/telemetry/crossfire.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/telemetry/crossfire.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/telemetry/crossfire.cpp 2017-11-10 17:23:25.000000000 +0000 @@ -153,7 +153,6 @@ break; case LINK_ID: - telemetryStreaming = TELEMETRY_TIMEOUT10ms; for (unsigned int i=0; i<=TX_SNR_INDEX; i++) { if (getCrossfireTelemetryValue<1>(3+i, value)) { if (i == TX_POWER_INDEX) { @@ -163,6 +162,7 @@ processCrossfireTelemetryValue(i, value); if (i == RX_QUALITY_INDEX) { telemetryData.rssi.set(value); + telemetryStreaming = TELEMETRY_TIMEOUT10ms; } } } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/telemetry/crossfire.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/telemetry/crossfire.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/telemetry/crossfire.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/telemetry/crossfire.h 2017-11-10 17:23:25.000000000 +0000 @@ -41,4 +41,21 @@ void crossfireSetDefault(int index, uint8_t id, uint8_t subId); bool isCrossfireOutputBufferAvailable(); +#if defined(PCBX7) || defined(PCBX10) +const uint32_t CROSSFIRE_BAUDRATES[] = { + 400000, + 115200, +}; +const uint8_t CROSSFIRE_FRAME_PERIODS[] = { + 4, + 16, +}; +#define CROSSFIRE_BAUDRATE CROSSFIRE_BAUDRATES[g_eeGeneral.telemetryBaudrate] +#define CROSSFIRE_FRAME_PERIOD CROSSFIRE_FRAME_PERIODS[g_eeGeneral.telemetryBaudrate] +#else +#define CROSSFIRE_BAUDRATE 400000 +#define CROSSFIRE_FRAME_PERIOD 4 // 4ms +#endif + + #endif // _CROSSFIRE_H_ diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/telemetry/frsky.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/telemetry/frsky.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/telemetry/frsky.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/telemetry/frsky.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -36,18 +36,6 @@ extern uint8_t TezRotary; #endif -// Receive buffer state machine state enum -enum FrSkyDataState { - STATE_DATA_IDLE, - STATE_DATA_START, - STATE_DATA_IN_FRAME, - STATE_DATA_XOR, -#if defined(TELEMETREZ) - STATE_DATA_PRIVATE_LEN, - STATE_DATA_PRIVATE_VALUE -#endif -}; - NOINLINE void processFrskyTelemetryData(uint8_t data) { static uint8_t dataState = STATE_DATA_IDLE; @@ -63,16 +51,9 @@ } #endif -#if defined(PCBX9E) && !defined(SIMU) && !defined(BLUETOOTH_CLI_PASSTHROUGH) - #define BLUETOOTH_BUFFER_LENGTH 20 - static uint8_t bluetoothBuffer[BLUETOOTH_BUFFER_LENGTH]; - static uint8_t bluetoothIndex = 0; - bluetoothBuffer[bluetoothIndex++] = data; - if (bluetoothIndex == BLUETOOTH_BUFFER_LENGTH) { - if (bluetoothReady()) { - bluetoothWrite(bluetoothBuffer, BLUETOOTH_BUFFER_LENGTH); - } - bluetoothIndex = 0; +#if defined(BLUETOOTH) + if (g_eeGeneral.bluetoothMode == BLUETOOTH_TELEMETRY && bluetoothState == BLUETOOTH_STATE_CONNECTED) { + bluetoothForwardTelemetry(data); } #endif diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/telemetry/frsky.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/telemetry/frsky.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/telemetry/frsky.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/telemetry/frsky.h 2017-10-31 16:16:43.000000000 +0000 @@ -24,6 +24,18 @@ #include "../definitions.h" #include "telemetry_holders.h" +// Receive buffer state machine state enum +enum FrSkyDataState { + STATE_DATA_IDLE, + STATE_DATA_START, + STATE_DATA_IN_FRAME, + STATE_DATA_XOR, +#if defined(TELEMETREZ) + STATE_DATA_PRIVATE_LEN, + STATE_DATA_PRIVATE_VALUE +#endif +}; + #define FRSKY_SPORT_BAUDRATE 57600 #define FRSKY_D_BAUDRATE 9600 @@ -143,6 +155,7 @@ #define DIY_LAST_ID 0x52ff #define DIY_STREAM_FIRST_ID 0x5000 #define DIY_STREAM_LAST_ID 0x50ff +#define FACT_TEST_ID 0xf000 #define RSSI_ID 0xf101 #define ADC1_ID 0xf102 #define ADC2_ID 0xf103 @@ -282,7 +295,7 @@ #define IS_SWR_VALUE_VALID() (true) #endif -#define IS_HIDDEN_TELEMETRY_VALUE(id) ((id == SP2UART_A_ID) || (id == SP2UART_B_ID) || (id == XJT_VERSION_ID) || (id == SWR_ID)) +#define IS_HIDDEN_TELEMETRY_VALUE(id) ((id == SP2UART_A_ID) || (id == SP2UART_B_ID) || (id == XJT_VERSION_ID) || (id == SWR_ID) || (id == FACT_TEST_ID)) enum AlarmLevel { alarm_off = 0, diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/telemetry/mavlink.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/telemetry/mavlink.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/telemetry/mavlink.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/telemetry/mavlink.h 2017-10-31 16:16:43.000000000 +0000 @@ -48,7 +48,16 @@ #define MAVLINK_END_UART_SEND(chan,len) SERIAL_end_uart_send() #define MAVLINK_SEND_UART_BYTES(chan,buf,len) SERIAL_send_uart_bytes(buf,len) +#if __clang__ +// clang does not like packed member access at all. Since mavlink is a 3rd party library, ignore the errors +#pragma clang diagnostic push +#pragma clang diagnostic ignored "-Waddress-of-packed-member" +#endif #include "GCS_MAVLink/include_v1.0/ardupilotmega/mavlink.h" +#if __clang__ +// Restore warnings about packed member access +#pragma clang diagnostic pop +#endif //#define MAVLINK_PARAMS //#define DUMP_RX_TX diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/telemetry/multi.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/telemetry/multi.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/telemetry/multi.cpp 2017-04-27 08:57:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/telemetry/multi.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -19,8 +19,10 @@ */ #include "opentx.h" #include "telemetry.h" +#include "multi.h" MultiModuleStatus multiModuleStatus; +MultiModuleSyncStatus multiSyncStatus; uint8_t multiBindStatus = MULTI_NORMAL_OPERATION; @@ -31,6 +33,8 @@ SpektrumTelemetry, DSMBindPacket, FlyskyIBusTelemetry, + ConfigCommand, + InputSync, }; enum MultiBufferState : uint8_t { @@ -68,10 +72,29 @@ multiModuleStatus.lastUpdate = get_tmr10ms(); if (wasBinding && !multiModuleStatus.isBinding() && multiBindStatus == MULTI_BIND_INITIATED) - multiBindStatus = MULTI_BIND_FINISHED; + multiBindStatus = MULTI_BIND_FINISHED; +} + +static void processMultiSyncPacket(const uint8_t *data) +{ + multiSyncStatus.lastUpdate = get_tmr10ms(); + multiSyncStatus.interval = data[4]; + multiSyncStatus.target = data[5]; +#if !defined(PPM_PIN_SERIAL) + auto oldlag = multiSyncStatus.inputLag; + (void) oldlag; +#endif + multiSyncStatus.calcAdjustedRefreshRate(data[0] << 8 | data[1], data[2] << 8 | data[3]); + +#if !defined(PPM_PIN_SERIAL) + TRACE("MP ADJ: rest: %d, lag %04d, diff: %04d target: %d, interval: %d, Refresh: %d, intAdjRefresh: %d, adjRefresh %d\r\n", modulePulsesData[EXTERNAL_MODULE].dsm2.rest, + multiSyncStatus.inputLag, oldlag-multiSyncStatus.inputLag, multiSyncStatus.target, multiSyncStatus.interval, multiSyncStatus.refreshRate, multiSyncStatus.adjustedRefreshRate/50, + multiSyncStatus.getAdjustedRefreshRate()); +#endif } + static void processMultiTelemetryPaket(const uint8_t *packet) { uint8_t type = packet[0]; @@ -112,7 +135,16 @@ if (len >= 4) sportProcessTelemetryPacket(data); else - TRACE("[MP] Received sm telemetry len %d < 4", len); + TRACE("[MP] Received sport telemetry len %d < 4", len); + break; + case InputSync: + if (len >= 6) + processMultiSyncPacket(data); + else + TRACE("[MP] Received input sync len %d < 6", len); + break; + case ConfigCommand: + // Just an ack to our command, ignore for now break; default: TRACE("[MP] Unkown multi packet type 0x%02X, len %d", type, len); @@ -122,31 +154,126 @@ // sprintf does not work AVR ARM // use a small helper function -static void appendInt(char* buf, uint32_t val) +static void appendInt(char *buf, uint32_t val) { - while(*buf) + while (*buf) buf++; - int len=1; - int32_t tmp = val / 10; - while (tmp) { - len++; - tmp /= 10; + strAppendUnsigned(buf, val); +} + +#define MIN_REFRESH_RATE 7000 + +void MultiModuleSyncStatus::calcAdjustedRefreshRate(uint16_t newRefreshRate, uint16_t newInputLag) +{ + // Check how far off we are from our target, positive means we are too slow, negative we are too fast + int lagDifference = newInputLag - inputLag; + + // The refresh rate that we target + // Below is least common multiple of MIN_REFRESH_RATE and requested rate + uint16_t targetRefreshRate = (uint16_t) (newRefreshRate * ((MIN_REFRESH_RATE / (newRefreshRate - 1)) + 1)); + + // Overflow, reverse sample + if (lagDifference < -targetRefreshRate/2) + lagDifference= -lagDifference; + + + // Reset adjusted refresh if rate has changed + if (newRefreshRate != refreshRate) { + refreshRate = newRefreshRate; + adjustedRefreshRate = targetRefreshRate; + if (adjustedRefreshRate >= 30000) + adjustedRefreshRate /= 2; + + // Our refresh rate in ps + adjustedRefreshRate*=1000; + return; } - buf[len]='\0'; - for (uint8_t i=1;i<=len; i++) { - div_t qr = div(val, 10); - char c = qr.rem + '0'; - buf[len - i] = c; - val = qr.quot; + // Caluclate how many samples went into the reported input Lag (*10) + int numsamples = interval * 10000 / targetRefreshRate; + + // Convert lagDifference to ps + lagDifference=lagDifference*1000; + + // Calculate the time we intentionally were late/early + if (inputLag > target*10 +30) + lagDifference += numsamples*500; + else if (inputLag < target*10 - 30) + lagDifference -= numsamples*500; + + // Caculate the time in ps each frame is to slow (positive), fast(negative) + int perframeps = lagDifference*10/ numsamples; + + if (perframeps > 20000) + perframeps = 20000; + + if (perframeps < -20000) + perframeps = -20000; + + adjustedRefreshRate =(adjustedRefreshRate + perframeps); + + // Safeguards + if (adjustedRefreshRate < 6*1000*1000) + adjustedRefreshRate = 6*1000*1000; + if (adjustedRefreshRate > 30*1000*1000) + adjustedRefreshRate = 30*1000*1000; + + inputLag = newInputLag; +} + +static uint8_t counter; + +uint16_t MultiModuleSyncStatus::getAdjustedRefreshRate() { + if (!isValid() || refreshRate == 0) + return 18000; + + + counter = (uint8_t) (counter + 1 % 10); + uint16_t rate = (uint16_t) ((adjustedRefreshRate + counter * 50) / 500); + // Check how far off we are from our target, positive means we are too slow, negative we are too fast + if (inputLag > target*10 +30) + return (uint16_t) (rate - 1); + else if (inputLag < target*10 - 30) + return (uint16_t) (rate + 1); + else + return rate; +} + + +static void prependSpaces(char * buf, int val) +{ + while (*buf) + buf++; + + int k=10000; + while(val/k==0 && k > 0) + { + *buf=' '; + buf++; + k/= 10; } + *buf='\0'; } +void MultiModuleSyncStatus::getRefreshString(char *statusText) +{ + if (!isValid()) { + return; + } + + strcpy(statusText, "L "); + prependSpaces(statusText, inputLag); + appendInt(statusText, inputLag); + strcat(statusText, "ns R "); + prependSpaces(statusText, adjustedRefreshRate/1000); + appendInt(statusText, (uint32_t) (adjustedRefreshRate / 1000)); + strcat(statusText, "ns"); +} void MultiModuleStatus::getStatusString(char *statusText) { - if (get_tmr10ms() - lastUpdate > 200) { + if (!isValid()) { #if defined(PCBTARANIS) || defined(PCBHORUS) if (IS_INTERNAL_MODULE_ENABLED()) strcpy(statusText, STR_DISABLE_INTERNAL); @@ -158,13 +285,20 @@ if (!protocolValid()) { strcpy(statusText, STR_PROTOCOL_INVALID); return; - } else if (!serialMode()) { + } + else if (!serialMode()) { strcpy(statusText, STR_MODULE_NO_SERIAL_MODE); return; - } else if (!inputDetected()) { + } + else if (!inputDetected()) { strcpy(statusText, STR_MODULE_NO_INPUT); return; } + else if(isWaitingforBind()) { + strcpy(statusText, STR_MODULE_WAITFORBIND); + return; + } + strcpy(statusText, "V"); appendInt(statusText, major); @@ -187,7 +321,8 @@ { if (telemetryRxBufferCount < TELEMETRY_RX_PACKET_SIZE) { telemetryRxBuffer[telemetryRxBufferCount++] = data; - } else { + } + else { TRACE("[MP] array size %d error", telemetryRxBufferCount); multiTelemetryBufferState = NoProtocolDetected; } @@ -216,12 +351,14 @@ case NoProtocolDetected: if (data == 'M') { multiTelemetryBufferState = MultiFirstByteReceived; - } else if (data == 0xAA || data == 0x7e) { + } + else if (data == 0xAA || data == 0x7e) { multiTelemetryBufferState = guessProtocol(); // Process the first byte by the protocol processMultiTelemetryData(data); - } else { + } + else { TRACE("[MP] invalid start byte 0x%02X", data); } break; @@ -262,12 +399,14 @@ telemetryRxBufferCount = 0; if (data == 'P') { multiTelemetryBufferState = ReceivingMultiProtocol; - } else if (data >= 5 && data <= 10) { + } + else if (data >= 5 && data <= 10) { // Protocol indented for er9x/ersky9, accept only 5-10 as packet length to have // a bit of validation multiTelemetryBufferState = ReceivingMultiStatus; - } else { + } + else { TRACE("[MP] invalid second byte 0x%02X", data); multiTelemetryBufferState = NoProtocolDetected; } @@ -280,9 +419,9 @@ case ReceivingMultiStatus: // Ignore multi status telemetryRxBuffer[telemetryRxBufferCount++] = data; - if (telemetryRxBufferCount>5) { + if (telemetryRxBufferCount > 5) { processMultiStatusPacket(telemetryRxBuffer); - telemetryRxBufferCount=0; + telemetryRxBufferCount = 0; multiTelemetryBufferState = NoProtocolDetected; } } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/telemetry/multi.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/telemetry/multi.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/telemetry/multi.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/telemetry/multi.h 2017-12-17 16:22:27.000000000 +0000 @@ -86,6 +86,30 @@ void processMultiTelemetryData(uint8_t data); +// This should be put into the Module definition if other modules gain this functionality +struct MultiModuleSyncStatus { + uint32_t adjustedRefreshRate; // in ps + tmr10ms_t lastUpdate; + uint16_t refreshRate; + uint16_t inputLag; + uint8_t interval; + uint8_t target; + + inline bool isValid() {return (get_tmr10ms() - lastUpdate < 100);} + void getRefreshString(char* refreshText); + uint16_t getAdjustedRefreshRate(); + void calcAdjustedRefreshRate(uint16_t newRefreshRate, uint16_t newInputLag); + + MultiModuleSyncStatus() { + // Initialise to a valid value + adjustedRefreshRate=9000 * 1000; + } + +}; + +extern MultiModuleSyncStatus multiSyncStatus; + + struct MultiModuleStatus { uint8_t major; @@ -98,10 +122,13 @@ void getStatusString(char* statusText); - inline bool isBinding() { return flags & 0x08; } - inline bool protocolValid() { return flags & 0x04; } - inline bool serialMode() { return flags & 0x02; } - inline bool inputDetected() { return flags & 0x01; } + inline bool isValid() { return (bool)(get_tmr10ms() - lastUpdate < 200); } + inline bool supportsFailsafe() { return (bool) (flags & 0x20); } + inline bool isWaitingforBind() { return (bool) (flags & 0x10); } + inline bool isBinding() { return (bool) (flags & 0x08); } + inline bool protocolValid() { return (bool) (flags & 0x04); } + inline bool serialMode() { return (bool) (flags & 0x02); } + inline bool inputDetected() { return (bool) (flags & 0x01); } }; extern MultiModuleStatus multiModuleStatus; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/telemetry/telemetry.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/telemetry/telemetry.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/telemetry/telemetry.cpp 2017-05-31 19:49:19.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/telemetry/telemetry.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -56,12 +56,6 @@ } #endif -#if defined(STM32) -#define IS_TELEMETRY_INTERNAL_MODULE (g_model.moduleData[INTERNAL_MODULE].rfProtocol != RF_PROTO_OFF) -#else -#define IS_TELEMETRY_INTERNAL_MODULE (false) -#endif - void processTelemetryData(uint8_t data) { #if defined(CROSSFIRE) @@ -174,12 +168,12 @@ } } } - if (sensor_lost && TELEMETRY_STREAMING()) { + if (sensor_lost && TELEMETRY_STREAMING() && !g_model.rssiAlarms.disabled) { audioEvent(AU_SENSOR_LOST); } #if defined(PCBTARANIS) || defined(PCBHORUS) - if ((g_model.moduleData[INTERNAL_MODULE].rfProtocol != RF_PROTO_OFF || g_model.moduleData[EXTERNAL_MODULE].type == MODULE_TYPE_XJT) && FRSKY_BAD_ANTENNA()) { + if ((IS_MODULE_PXX(INTERNAL_MODULE) || IS_MODULE_PXX(EXTERNAL_MODULE)) && FRSKY_BAD_ANTENNA()) { AUDIO_SWR_RED(); POPUP_WARNING(STR_WARNING); const char * w = STR_ANTENNAPROBLEM; @@ -188,27 +182,29 @@ } #endif - if (TELEMETRY_STREAMING()) { - if (getRssiAlarmValue(1) && TELEMETRY_RSSI() < getRssiAlarmValue(1)) { - AUDIO_RSSI_RED(); - SCHEDULE_NEXT_ALARMS_CHECK(10/*seconds*/); - } - else if (getRssiAlarmValue(0) && TELEMETRY_RSSI() < getRssiAlarmValue(0)) { - AUDIO_RSSI_ORANGE(); - SCHEDULE_NEXT_ALARMS_CHECK(10/*seconds*/); + if (!g_model.rssiAlarms.disabled) { + if (TELEMETRY_STREAMING()) { + if (TELEMETRY_RSSI() < g_model.rssiAlarms.getCriticalRssi() ) { + AUDIO_RSSI_RED(); + SCHEDULE_NEXT_ALARMS_CHECK(10/*seconds*/); + } + else if (TELEMETRY_RSSI() < g_model.rssiAlarms.getWarningRssi() ) { + AUDIO_RSSI_ORANGE(); + SCHEDULE_NEXT_ALARMS_CHECK(10/*seconds*/); + } } - } - } - if (TELEMETRY_STREAMING()) { - if (telemetryState == TELEMETRY_KO) { - AUDIO_TELEMETRY_BACK(); + if (TELEMETRY_STREAMING()) { + if (telemetryState == TELEMETRY_KO) { + AUDIO_TELEMETRY_BACK(); + } + telemetryState = TELEMETRY_OK; + } + else if (telemetryState == TELEMETRY_OK) { + telemetryState = TELEMETRY_KO; + AUDIO_TELEMETRY_LOST(); + } } - telemetryState = TELEMETRY_OK; - } - else if (telemetryState == TELEMETRY_OK) { - telemetryState = TELEMETRY_KO; - AUDIO_TELEMETRY_LOST(); } #endif } @@ -408,7 +404,7 @@ } #endif -#if defined(SERIAL2) +#if defined(SERIAL2) || defined(PCBSKY9X) else if (protocol == PROTOCOL_FRSKY_D_SECONDARY) { telemetryPortInit(0, TELEMETRY_SERIAL_DEFAULT); serial2TelemetryInit(PROTOCOL_FRSKY_D_SECONDARY); @@ -439,10 +435,12 @@ } #endif +#if !defined(CPUARM) NOINLINE uint8_t getRssiAlarmValue(uint8_t alarm) { return (45 - 3*alarm + g_model.frsky.rssiAlarms[alarm].value); } +#endif #if defined(LOG_TELEMETRY) && !defined(SIMU) extern FIL g_telemetryFile; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/telemetry/telemetry.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/telemetry/telemetry.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/telemetry/telemetry.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/telemetry/telemetry.h 2017-12-17 16:22:27.000000000 +0000 @@ -197,4 +197,10 @@ extern Fifo * luaInputTelemetryFifo; #endif +#if defined(STM32) +#define IS_TELEMETRY_INTERNAL_MODULE() (g_model.moduleData[INTERNAL_MODULE].type == MODULE_TYPE_XJT) +#else +#define IS_TELEMETRY_INTERNAL_MODULE() (false) +#endif + #endif // _TELEMETRY_H_ diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/telemetry/telemetry_sensors.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/telemetry/telemetry_sensors.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/telemetry/telemetry_sensors.cpp 2017-05-31 19:49:19.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/telemetry/telemetry_sensors.cpp 2017-11-10 17:23:25.000000000 +0000 @@ -93,6 +93,12 @@ newVal = 0; } else if (unit == UNIT_GPS_LATITUDE) { +#if defined(INTERNAL_GPS) + if (gpsData.fix) { + pilotLatitude = gpsData.latitude; + distFromEarthAxis = getDistFromEarthAxis(pilotLatitude); + } +#endif if (!pilotLatitude) { pilotLatitude = newVal; distFromEarthAxis = getDistFromEarthAxis(newVal); @@ -102,6 +108,11 @@ return; } else if (unit == UNIT_GPS_LONGITUDE) { +#if defined(INTERNAL_GPS) + if (gpsData.fix) { + pilotLongitude = gpsData.longitude; + } +#endif if (!pilotLongitude) { pilotLongitude = newVal; } @@ -304,12 +315,16 @@ dist = gpsItem.distFromEarthAxis * angle / 1000000; result += dist*dist; + // Length on ground (ignoring curvature of the earth) + result = isqrt32(result); + if (altItem) { dist = abs(altItem->value) / g_model.telemetrySensors[sensor.dist.alt-1].getPrecDivisor(); - result += dist*dist; + result = dist*dist + result*result; + result = isqrt32(result); } - setValue(sensor, isqrt32(result), UNIT_METERS); + setValue(sensor, result, UNIT_METERS); } break; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/templates.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/templates.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/templates.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/templates.cpp 2017-10-31 16:16:43.000000000 +0000 @@ -102,6 +102,7 @@ memclear(g_model.curves, sizeof(g_model.curves) + sizeof(g_model.points)); // clear all curves } +#if defined(CURVES) void setCurve(uint8_t c, const pm_int8_t ar[]) { int8_t * cv = curveAddress(c); @@ -109,6 +110,7 @@ cv[i] = pgm_read_byte(&ar[i]); } } +#endif void setLogicalSwitch(uint8_t idx, uint8_t func, int8_t v1, int8_t v2) { @@ -140,7 +142,9 @@ switch (idx) { case TMPL_CLEAR_MIXES: case TMPL_SIMPLE_4CH: +#if defined(HELI) && defined(CURVES) case TMPL_HELI_SETUP: +#endif clearMixes(); break; } @@ -195,6 +199,7 @@ md=setDest(5, MIXSRC_Thr); md->weight= 55; break; +#if defined(HELI) && defined(CURVES) // Heli Setup case TMPL_HELI_SETUP: clearCurves(); @@ -242,6 +247,7 @@ setCurve(4, heli_ar5); setCurve(5, heli_ar5); break; +#endif // Servo Test case TMPL_SERVO_TEST: diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/templates.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/templates.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/templates.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/templates.h 2017-10-31 16:16:43.000000000 +0000 @@ -66,7 +66,9 @@ TMPL_V_TAIL, TMPL_ELEVON_DELTA, TMPL_ECCPM, +#if defined(HELI) && defined(CURVES) TMPL_HELI_SETUP, +#endif TMPL_SERVO_TEST, TMPL_COUNT }; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/tests/gtests.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/tests/gtests.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/tests/gtests.h 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/tests/gtests.h 2017-11-15 20:54:40.000000000 +0000 @@ -49,6 +49,9 @@ #endif generalDefault(); g_eeGeneral.templateSetup = 0; + for (int i=0; iSD"," [ENTER Long] Backup EEPROM->SD-Karte") -#define TR_FACTORYRESET TR("[MENU Long] Werksreset"," [MENU Long] Komplett reset") +#define TR_FACTORYRESET TR("[MENU Long] Werksreset"," [MENU Long] Auf Werkseinstellungen") #define TR_CONFIRMRESET TR("Alles löschen? ","ALLE Modelle+Einst. löschen?") #define TR_TO_MANY_LUA_SCRIPTS "Zu viele Lua-Skripte!" @@ -1210,9 +1250,9 @@ #define TR_BEEP_VOLUME "Beep-Lautst." #define TR_WAV_VOLUME "Wave-Lautst." -#define TR_BG_VOLUME "Hintergr-Lautst." +#define TR_BG_VOLUME TR("Hintergr-Lautst.", "Hintergrund-Lautstärke") -#define TR_TOP_BAR "----Infozeile----" +#define TR_TOP_BAR "Infozeile" #define TR_ALTITUDE INDENT "Höhenanzeige" #define TR_SCALE "Skalieren" #define TR_VIEW_CHANNELS "Zeige Kanäle" @@ -1239,7 +1279,7 @@ #define TR_SERVOS_OK "Servos OK" #define TR_SERVOS_KO "Servos KO" #define TR_INVERTED_SERIAL INDENT "Invert." -#define TR_IGNORE_INSTANCE TR(INDENT "Keine ID", INDENT "Keine Multisensor-ID") //unklar +#define TR_IGNORE_INSTANCE TR(INDENT "Ignr. Inst.", INDENT "Ignor. Instanzen") #define TR_DISCOVER_SENSORS INDENT "Start Sensorsuche" #define TR_STOP_DISCOVER_SENSORS INDENT "Stop Sensorsuche" #define TR_DELETE_ALL_SENSORS INDENT "Lösche alle Sensoren" diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/translations/en.h.txt opentx-companion22-2.2.1~ppa01~xenial/radio/src/translations/en.h.txt --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/translations/en.h.txt 2017-05-31 19:49:19.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/translations/en.h.txt 2017-12-17 16:22:27.000000000 +0000 @@ -98,8 +98,11 @@ #define LEN_COUNTRYCODES TR("\002", "\007") #define TR_COUNTRYCODES TR("US""JP""EU", "America""Japan\0 ""Europe\0") +#define LEN_USBMODES TR("\006", "\010") +#define TR_USBMODES TR("Ask\0 ""Joyst\0""SDCard""Serial", "Ask\0 ""Joystick""Storage\0""Serial\0 ") + #define LEN_TARANIS_PROTOCOLS "\004" -#define TR_TARANIS_PROTOCOLS "OFF\0""PPM\0""XJT\0""DSM2""CRSF""MULT" +#define TR_TARANIS_PROTOCOLS "OFF\0""PPM\0""XJT\0""DSM2""CRSF""MULT""R9M\0""SBUS" #define LEN_TELEMETRY_PROTOCOLS "\017" #define TR_TELEMETRY_PROTOCOLS "FrSky S.PORT\0 ""FrSky D\0 ""FrSky D (cable)""TBS Crossfire\0 ""Spektrum\0 ""AFHDS2A IBUS\0 ""Multi Telemetry" @@ -111,7 +114,7 @@ #define TR_DSM_PROTOCOLS "LP45""DSM2""DSMX" #define LEN_MULTI_PROTOCOLS "\006" -#define TR_MULTI_PROTOCOLS "FlySky""Hubsan""FrSky\0""Hisky\0""V2x2\0 ""DSM\0 ""Devo\0 ""YD717\0""KN\0 ""SymaX\0""SLT\0 ""CX10\0 ""CG023\0""Bayang""ESky\0 ""MT99XX""MJXQ\0 ""Shenqi""FY326\0""SFHSS\0""J6 PRO""FQ777\0""Assan\0""Hontai""OLRS\0 ""FS 2A\0""Q2x2\0 ""Walk.\0""Q303\0 ""GW008\0""DM002\0" +#define TR_MULTI_PROTOCOLS "FlySky""Hubsan""FrSky\0""Hisky\0""V2x2\0 ""DSM\0 ""Devo\0 ""YD717\0""KN\0 ""SymaX\0""SLT\0 ""CX10\0 ""CG023\0""Bayang""ESky\0 ""MT99XX""MJXQ\0 ""Shenqi""FY326\0""SFHSS\0""J6 PRO""FQ777\0""Assan\0""Hontai""OLRS\0 ""FS 2A\0""Q2x2\0 ""Walk.\0""Q303\0 ""GW008\0""DM002\0""Cabell""Esky15""H8 3D\0" #define TR_MULTI_CUSTOM "Custom" @@ -413,9 +416,16 @@ #define LEN_GPSFORMAT "\004" #define TR_GPSFORMAT "DMS\0""NMEA" -#define LEN2_VTEMPLATES 13 -#define LEN_VTEMPLATES "\015" -#define TR_VTEMPLATES "Clear Mixes\0\0""Simple 4-CH \0""Sticky-T-Cut\0""V-Tail \0""Elevon\\Delta\0""eCCPM \0""Heli Setup \0""Servo Test \0" +#define LEN2_VTEMPLATES 12 +#define LEN_VTEMPLATES "\014" +#define TR_TEMPLATE_CLEAR_MIXES "Clear Mixes " +#define TR_TEMPLATE_SIMPLE_4CH "Simple 4-CH " +#define TR_TEMPLATE_STICKY_TCUT "Sticky-T-Cut" +#define TR_TEMPLATE_VTAIL "V-Tail " +#define TR_TEMPLATE_DELTA "Elevon\\Delta" +#define TR_TEMPLATE_ECCPM "eCCPM " +#define TR_TEMPLATE_HELI "Heli Setup " +#define TR_TEMPLATE_SERVO_TEST "Servo Test " #define LEN_VSWASHTYPE "\004" #define TR_VSWASHTYPE "---\0""120\0""120X""140\0""90\0" @@ -552,7 +562,8 @@ #define TR_VTRAINER_SLAVE_JACK "Slave/Jack\0 " #define TR_VTRAINER_MASTER_SBUS_MODULE "Master/SBUS Module" #define TR_VTRAINER_MASTER_CPPM_MODULE "Master/CPPM Module" -#define TR_VTRAINER_MASTER_BATTERY "Master/Battery\0" +#define TR_VTRAINER_MASTER_BATTERY "Master/Battery\0 " +#define TR_VTRAINER_BLUETOOTH TR("Master/BT\0 ""Slave/BT\0", "Master/Bluetooth\0 ""Slave/Bluetooth\0 ") #define LEN_VFAILSAFE "\011" #define TR_VFAILSAFE "Not set\0 ""Hold\0 ""Custom\0 ""No pulses""Receiver\0" @@ -642,6 +653,8 @@ #define TR_PROTO TR(INDENT "Proto", INDENT "Protocol") #if defined(CPUARM) #define TR_PPMFRAME INDENT "PPM frame" + #define TR_REFRESHRATE TR(INDENT "Refresh", INDENT "Refresh rate") + #define STR_WARN_BATTVOLTAGE TR(INDENT "Output is VBAT: ", INDENT "Warning: output level is VBAT: ") #else #define TR_PPMFRAME "PPM frame" #endif @@ -707,6 +720,9 @@ #define TR_INACTIVITYALARM INDENT "Inactivity" #define TR_MEMORYWARNING INDENT "Memory low" #define TR_ALARMWARNING INDENT "Sound off" +#define TR_RSSISHUTDOWNALARM TR(INDENT "Rssi Shutdown", INDENT "Check Rssi on Shutdown") +#define TR_MODEL_STILL_POWERED "Model still powered" +#define TR_PRESS_ENTER_TO_CONFIRM "Press enter to confirm" #define TR_RENAVIG "RotEnc Navig" #define TR_THROTTLE_LABEL "Throttle" #define TR_THROTTLEREVERSE TR("T-Reverse", INDENT "Reverse") @@ -848,17 +864,25 @@ #define TR_MULTI_AUTOBIND TR(INDENT "Autobind",INDENT "Bind on powerup") #define TR_MULTI_DSM_AUTODTECT TR(INDENT "Autodetect", INDENT "Autodetect format") #define TR_MULTI_LOWPOWER TR(INDENT "Low power", INDENT "Low power mode") +#define TR_MODULE_TELEMETRY TR(INDENT "Mod telem.", INDENT "Module telemetry") #define TR_DISABLE_INTERNAL TR("Disable int.", "Disable internal RF") #define TR_MODULE_NO_SERIAL_MODE TR("!serial mode", "Not in serial mode") #define TR_MODULE_NO_INPUT TR("No input", "No serial input") #define TR_MODULE_NO_TELEMETRY TR3("No telemetry", "No MULTI_TELEMETRY", "No MULTI_TELEMETRY detected") +#define TR_MODULE_WAITFORBIND "Bind to load protocol" #define TR_MODULE_BINDING TR("Bind...","Binding") -#define TR_BINDING_MODE1 "Ch1-8 Telem ON" -#define TR_BINDING_MODE2 "Ch1-8 Telem OFF" -#define TR_BINDING_MODE3 "Ch9-16 Telem ON" -#define TR_BINDING_MODE4 "Ch9-16 Telem OFF" +#define TR_BINDING_CH1_8_TELEM_ON "Ch1-8 Telem ON" +#define TR_BINDING_CH1_8_TELEM_OFF "Ch1-8 Telem OFF" +#define TR_BINDING_CH9_16_TELEM_ON "Ch9-16 Telem ON" +#define TR_BINDING_CH9_16_TELEM_OFF "Ch9-16 Telem OFF" +#define TR_BINDING_25MW_CH1_8_TELEM_OFF TR("25mW Ch1-8 Tel OFF", "25mW Ch1-8 Telem OFF") +#define TR_BINDING_25MW_CH1_8_TELEM_ON TR("25mW Ch1-8 Tel ON", "25mW Ch1-8 Telem ON") +#define TR_BINDING_500MW_CH1_8_TELEM_OFF TR("500mW Ch1-8 Tel OFF", "500mW Ch1-8 Telem OFF") +#define TR_BINDING_500MW_CH9_16_TELEM_OFF TR("500mW Ch9-16 Tel OFF", "500mW Ch9-16 Telem OFF") +#define TR_BINDING_OPTION "Set at bind" #define TR_PROTOCOL_INVALID TR("Prot. invalid", "Protocol invalid") #define TR_MODULE_STATUS TR(INDENT "Status", INDENT "Module Status") +#define TR_MODULE_SYNC TR(INDENT "Sync", INDENT "Module Sync") #define TR_MULTI_SERVOFREQ TR(INDENT "Servo rate", INDENT "Servo update rate") #define TR_SYNCMENU "[Sync]" #define TR_LIMIT INDENT "Limit" @@ -873,7 +897,7 @@ #define TR_POWEROFF "\027Power OFF..." #define TR_SHUTDOWN "SHUTTING DOWN" #define TR_SAVEMODEL "Saving model settings" -#define TR_BATT_CALIB "Battery calib" +#define TR_BATT_CALIB TR("Battery calib", "Battery calibration") #define TR_CURRENT_CALIB "Current calib" #define TR_VOLTAGE TR(INDENT "Voltage", INDENT "Voltage source") #define TR_CURRENT TR(INDENT "Current", INDENT "Current source") @@ -902,6 +926,8 @@ #define TR_ALARMSWARN "ALARMS" #define TR_SWITCHWARN TR("SWITCH", "CONTROL") #define TR_FAILSAFEWARN "FAILSAFE" +#define TR_NIGHTLY_WARNING TR("NIGHTLY", "NIGHTLY BUILD") +#define TR_NIGHTLY_NOTSAFE "Version not safe to fly" #define TR_WRONG_SDCARDVERSION TR("Expected ver: ","Expected version: ") #define TR_WRONG_PCBREV "Wrong PCB detected" #define TR_EMERGENCY_MODE "EMERGENCY MODE" @@ -948,7 +974,13 @@ #define TR_FORMATTING "Formatting..." #define TR_TEMP_CALIB "Temp. Calib" #define TR_TIME "Time" +#define TR_MAXBAUDRATE "Max bauds" + +#define TR_BLUETOOTH "Bluetooth" #define TR_BAUDRATE "BT Baudrate" +#define LEN_BLUETOOTH_MODES "\011" +#define TR_BLUETOOTH_MODES "---\0 ""Telemetry""Trainer\0" + #define TR_SD_INFO_TITLE "SD INFO" #define TR_SD_TYPE "Type:" #define TR_SD_SPEED "Speed:" @@ -982,6 +1014,7 @@ #define TR_MENUSENSOR "SENSOR" #define TR_SENSOR "SENSOR" #define TR_COUNTRYCODE "Country code" +#define TR_USBMODE "USB Mode" #define TR_VOICELANG "Voice language" #define TR_UNITSSYSTEM "Units" #define TR_EDIT "Edit" @@ -999,6 +1032,9 @@ #define TR_RESET_TELEMETRY "Reset telemetry" #define TR_STATISTICS "Statistics" #define TR_ABOUT_US "About" +#define TR_USB_JOYSTICK "USB Joystick (HID)" +#define TR_USB_MASS_STORAGE "USB Storage (SD)" +#define TR_USB_SERIAL "USB Serial (Debug)" #define TR_SETUP_SCREENS "Setup screens" #define TR_MONITOR_SCREENS "Monitors" #define TR_AND_SWITCH "AND switch" @@ -1011,9 +1047,9 @@ #define TR_MODULE_RANGE BUTTON(TR("Rng", "Range")) #define TR_RESET_BTN BUTTON("Reset") #define TR_SET BUTTON("Set") -#define TR_TRAINER "Trainer port" +#define TR_TRAINER "Trainer" #define TR_ANTENNAPROBLEM CENTER "TX antenna problem!" -#define TR_MODELIDUSED TR("ID already used","Model ID already used") +#define TR_MODELIDUSED TR("ID used in:","Receiver ID used in:") #define TR_MODULE INDENT "Module" #define TR_TELEMETRY_TYPE TR("Type", "Telemetry type") #define TR_TELEMETRY_SENSORS "Sensors" @@ -1027,6 +1063,9 @@ #define TR_ANTENNACONFIRM2 "Make sure antenna is installed!" #define TR_LOWALARM INDENT "Low alarm" #define TR_CRITICALALARM INDENT "Critical alarm" +#define TR_RSSIALARM_WARN "RSSI" +#define TR_NO_RSSIALARM TR(INDENT "Alarms disabled", "Telemetry alarms disabled") +#define TR_DISABLE_ALARM TR(INDENT "Disable alarms", INDENT "Disable telemetry alarms") #define TR_ENABLE_POPUP "Enable popup" #define TR_DISABLE_POPUP "Disable popup" #define TR_POPUP "Popup" @@ -1198,7 +1237,7 @@ #define TR_BEEP_VOLUME "Beep volume" #define TR_WAV_VOLUME "Wav volume" -#define TR_BG_VOLUME "Bg volume" +#define TR_BG_VOLUME TR("Bg volume", "Background Volume") #define TR_TOP_BAR "Top bar" #define TR_ALTITUDE INDENT "Altitude" diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/translations/es.h.txt opentx-companion22-2.2.1~ppa01~xenial/radio/src/translations/es.h.txt --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/translations/es.h.txt 2017-05-31 19:49:19.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/translations/es.h.txt 2017-12-17 16:22:27.000000000 +0000 @@ -94,8 +94,11 @@ #define LEN_COUNTRYCODES TR("\002", "\007") #define TR_COUNTRYCODES TR("US""JP""EU", "America""Japon\0 ""Europa\0") +#define LEN_USBMODES TR("\006", "\010") +#define TR_USBMODES TR("Ask\0 ""Joyst\0""SDCard""Serial", "Ask\0 ""Joystick""Storage\0""Serial\0 ") + #define LEN_TARANIS_PROTOCOLS "\004" -#define TR_TARANIS_PROTOCOLS "OFF\0""PPM\0""XJT\0""DSM2""CRSF""MULT" +#define TR_TARANIS_PROTOCOLS "OFF\0""PPM\0""XJT\0""DSM2""CRSF""MULT""R9M\0""SBUS" #define LEN_TELEMETRY_PROTOCOLS "\017" #define TR_TELEMETRY_PROTOCOLS "FrSky S.PORT\0 ""FrSky D\0 ""FrSky D (cable)""TBS Crossfire\0 ""Spektrum\0 ""AFHDS2A IBUS\0 ""Multi Telemetry" @@ -107,7 +110,7 @@ #define TR_DSM_PROTOCOLS "LP45""DSM2""DSMX" #define LEN_MULTI_PROTOCOLS "\006" -#define TR_MULTI_PROTOCOLS "FlySky""Hubsan""FrSky\0""Hisky\0""V2x2\0 ""DSM\0 ""Devo\0 ""YD717\0""KN\0 ""SymaX\0""SLT\0 ""CX10\0 ""CG023\0""Bayang""ESky\0 ""MT99XX""MJXQ\0 ""Shenqi""FY326\0""SFHSS\0""J6 PRO""FQ777\0""Assan\0""Hontai""OLRS\0 ""FS 2A\0""Q2x2\0 ""Walk.\0""Q303\0 ""GW008\0""DM002\0" +#define TR_MULTI_PROTOCOLS "FlySky""Hubsan""FrSky\0""Hisky\0""V2x2\0 ""DSM\0 ""Devo\0 ""YD717\0""KN\0 ""SymaX\0""SLT\0 ""CX10\0 ""CG023\0""Bayang""ESky\0 ""MT99XX""MJXQ\0 ""Shenqi""FY326\0""SFHSS\0""J6 PRO""FQ777\0""Assan\0""Hontai""OLRS\0 ""FS 2A\0""Q2x2\0 ""Walk.\0""Q303\0 ""GW008\0""DM002\0""Cabell""Esky15""H8 3D\0" #define TR_MULTI_CUSTOM "Custom" @@ -431,9 +434,16 @@ #define LEN_GPSFORMAT "\004" #define TR_GPSFORMAT "HMS NMEA" -#define LEN2_VTEMPLATES 13 -#define LEN_VTEMPLATES "\015" -#define TR_VTEMPLATES "Elim Mezcla\0\0""Simple 4-CH \0""Anular Motor\0""Cola en V \0""Elevon\\Delta\0""eCCPM \0""Heli Setup \0""Servo Test \0" +#define LEN2_VTEMPLATES 12 +#define LEN_VTEMPLATES "\014" +#define TR_TEMPLATE_CLEAR_MIXES "Elim Mezcla\0" +#define TR_TEMPLATE_SIMPLE_4CH "Simple 4-CH " +#define TR_TEMPLATE_STICKY_TCUT "Anular Motor" +#define TR_TEMPLATE_VTAIL "Cola en V " +#define TR_TEMPLATE_DELTA "Elevon\\Delta" +#define TR_TEMPLATE_ECCPM "eCCPM " +#define TR_TEMPLATE_HELI "Heli Setup " +#define TR_TEMPLATE_SERVO_TEST "Servo Test " #define LEN_VSWASHTYPE "\004" #define TR_VSWASHTYPE "---\0""120\0""120X""140\0""90\0" @@ -540,7 +550,8 @@ #define TR_VTRAINER_SLAVE_JACK "Esclav/Jack\0 " #define TR_VTRAINER_MASTER_SBUS_MODULE "Master/SBUS Module" #define TR_VTRAINER_MASTER_CPPM_MODULE "Master/CPPM Module" -#define TR_VTRAINER_MASTER_BATTERY "Master/Battery\0" +#define TR_VTRAINER_MASTER_BATTERY "Master/Battery\0 " +#define TR_VTRAINER_BLUETOOTH TR("Master/BT\0 ""Slave/BT\0", "Master/Bluetooth\0 ""Slave/Bluetooth\0 ") #define LEN_VFAILSAFE "\011" #define TR_VFAILSAFE "Not set\0 ""Guardar\0 ""Adaptar\0 ""Sin pulso""Receiver\0" @@ -632,6 +643,8 @@ #endif #define TR_PROTO TR(INDENT"Proto",INDENT"Protocol") #define TR_PPMFRAME "Trama PPM" +#define TR_REFRESHRATE TR(INDENT "Refresh", INDENT "Refresh rate") +#define STR_WARN_BATTVOLTAGE TR(INDENT "Output is VBAT: ", INDENT "Warning: output level is VBAT: ") #define TR_MS "ms" #define TR_SWITCH "Interr" #define TR_TRIMS "Trims" @@ -694,6 +707,9 @@ #define TR_INACTIVITYALARM INDENT"Inactividad" #define TR_MEMORYWARNING INDENT"Memoria Baja" #define TR_ALARMWARNING INDENT"Sin Sonido" +#define TR_RSSISHUTDOWNALARM TR(INDENT "Rssi Shutdown", INDENT "Check Rssi on Shutdown") +#define TR_MODEL_STILL_POWERED "Model still powered" +#define TR_PRESS_ENTER_TO_CONFIRM "Press enter to confirm" #define TR_RENAVIG "RotEnc Navig" #define TR_THROTTLE_LABEL "Throttle" #define TR_THROTTLEREVERSE TR("Invert_Acel", INDENT "Invertir Acel.") @@ -824,17 +840,25 @@ #define TR_MULTI_AUTOBIND TR(INDENT "Autobind",INDENT "Bind on powerup") #define TR_MULTI_DSM_AUTODTECT TR(INDENT "Autodetect", INDENT "Autodetect format") #define TR_MULTI_LOWPOWER TR(INDENT "Low power", INDENT "Low power mode") -#define TR_DISABLE_INTERNAL TR("Disable int. RF", "Disable internal RF") +#define TR_MODULE_TELEMETRY TR(INDENT "Mod telem.", INDENT "Module telemetry") +#define TR_DISABLE_INTERNAL TR("Disable int. RF", "Disable internal RF") #define TR_MODULE_NO_SERIAL_MODE TR("!serial mode", "Not in serial mode") #define TR_MODULE_NO_INPUT TR("No input", "No serial input") #define TR_MODULE_NO_TELEMETRY TR3( "No telmetry", "No MULTI_TELEMETRY", "No telemetry (enable MULTI_TELEMETRY)") +#define TR_MODULE_WAITFORBIND "Bind to load protocol" #define TR_MODULE_BINDING "Binding" -#define TR_BINDING_MODE1 "Ch1-8 Telem ON" -#define TR_BINDING_MODE2 "Ch1-8 Telem OFF" -#define TR_BINDING_MODE3 "Ch9-16 Telem ON" -#define TR_BINDING_MODE4 "Ch9-16 Telem OFF" +#define TR_BINDING_CH1_8_TELEM_ON "Ch1-8 Telem ON" +#define TR_BINDING_CH1_8_TELEM_OFF "Ch1-8 Telem OFF" +#define TR_BINDING_CH9_16_TELEM_ON "Ch9-16 Telem ON" +#define TR_BINDING_CH9_16_TELEM_OFF "Ch9-16 Telem OFF" +#define TR_BINDING_25MW_CH1_8_TELEM_OFF TR("25mW Ch1-8 Tel OFF", "25mW Ch1-8 Telem OFF") +#define TR_BINDING_25MW_CH1_8_TELEM_ON TR("25mW Ch1-8 Tel ON", "25mW Ch1-8 Telem ON") +#define TR_BINDING_500MW_CH1_8_TELEM_OFF TR("500mW Ch1-8 Tel OFF", "500mW Ch1-8 Telem OFF") +#define TR_BINDING_500MW_CH9_16_TELEM_OFF TR("500mW Ch9-16 Tel OFF", "500mW Ch9-16 Telem OFF") +#define TR_BINDING_OPTION "Set at bind" #define TR_PROTOCOL_INVALID TR("Prot. invalid", "Protocol invalid") #define TR_MODULE_STATUS TR(INDENT "Status", INDENT "Module Status") +#define TR_MODULE_SYNC TR(INDENT "Sync", INDENT "Module Sync") #define TR_MULTI_SERVOFREQ TR(INDENT "Servo rate", INDENT "Servo update rate") #define TR_SYNCMENU "Sync " TR_ENTER #define TR_LIMIT INDENT"Limite" @@ -878,6 +902,8 @@ #define TR_ALARMSWARN "ALARMAS" #define TR_SWITCHWARN "INTERPTOR" #define TR_FAILSAFEWARN "FAILSAFE" +#define TR_NIGHTLY_WARNING TR("NIGHTLY", "NIGHTLY BUILD") +#define TR_NIGHTLY_NOTSAFE "Version not safe to fly" #define TR_WRONG_SDCARDVERSION TR("Expected ver: ","Expected version: ") #define TR_WRONG_PCBREV "Wrong PCB detected" #define TR_EMERGENCY_MODE "EMERGENCY MODE" @@ -924,7 +950,13 @@ #define TR_FORMATTING "Formateando.." #define TR_TEMP_CALIB "Temp. Calib" #define TR_TIME "Hora" +#define TR_MAXBAUDRATE "Max bauds" + +#define TR_BLUETOOTH "Bluetooth" #define TR_BAUDRATE "BT Baudrate" +#define LEN_BLUETOOTH_MODES "\011" +#define TR_BLUETOOTH_MODES "---\0 ""Telemetry""Trainer\0" + #define TR_SD_INFO_TITLE "SD INFO" #define TR_SD_TYPE "Tipo:" #define TR_SD_SPEED "Velocidad:" @@ -958,6 +990,7 @@ #define TR_MENUSENSOR "SENSOR" #define TR_SENSOR "SENSOR" #define TR_COUNTRYCODE "Codigo Pais" +#define TR_USBMODE "USB Mode" #define TR_VOICELANG "Idioma voces" #define TR_UNITSSYSTEM "Unidades" #define TR_EDIT "Editar" @@ -975,7 +1008,10 @@ #define TR_RESET_TELEMETRY "Reset Telemetria" #define TR_STATISTICS "Estadisticas" #define TR_ABOUT_US "Nosotros" -#define TR_SETUP_SCREENS "Setup screens" +#define TR_USB_JOYSTICK "USB Joystick (HID)" +#define TR_USB_MASS_STORAGE "USB Storage (SD)" +#define TR_USB_SERIAL "USB Serial (Debug)" +#define TR_SETUP_SCREENS "Setup screens" #define TR_MONITOR_SCREENS "Monitors" #define TR_AND_SWITCH "AND Inter." #define TR_SF "CF" @@ -1003,6 +1039,9 @@ #define TR_ANTENNACONFIRM2 "Make sure antenna is installed!" #define TR_LOWALARM INDENT "Alarma baja" #define TR_CRITICALALARM INDENT "Alarma Critica" +#define TR_RSSIALARM_WARN TR("RSSI","TELEMETRY RSSI") +#define TR_NO_RSSIALARM TR(INDENT "Alarms disabled", INDENT "Telemetry alarms disabled") +#define TR_DISABLE_ALARM TR(INDENT "Disable alarms", INDENT "Disable telemetry alarms") #define TR_ENABLE_POPUP "Enable Popup" #define TR_DISABLE_POPUP "Disable Popup" #define TR_POPUP "Popup" diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/translations/fi.h.txt opentx-companion22-2.2.1~ppa01~xenial/radio/src/translations/fi.h.txt --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/translations/fi.h.txt 2017-05-31 19:49:19.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/translations/fi.h.txt 2017-12-17 16:22:27.000000000 +0000 @@ -94,8 +94,11 @@ #define LEN_COUNTRYCODES TR("\002", "\007") #define TR_COUNTRYCODES TR("US""JP""EU", "Amerikk""Japani\0""Euroopp") +#define LEN_USBMODES TR("\006", "\010") +#define TR_USBMODES TR("Ask\0 ""Joyst\0""SDCard""Serial", "Ask\0 ""Joystick""Storage\0""Serial\0 ") + #define LEN_TARANIS_PROTOCOLS "\004" -#define TR_TARANIS_PROTOCOLS "OFF\0""PPM\0""XJT\0""DSM2""CRSF""MULT" +#define TR_TARANIS_PROTOCOLS "OFF\0""PPM\0""XJT\0""DSM2""CRSF""MULT""R9M\0""SBUS" #define LEN_TELEMETRY_PROTOCOLS "\017" #define TR_TELEMETRY_PROTOCOLS "FrSky S.PORT\0 ""FrSky D\0 ""FrSky D (cable)""TBS Crossfire\0 ""Spektrum\0 ""AFHDS2A IBUS\0 ""Multi Telemetry" @@ -107,7 +110,7 @@ #define TR_DSM_PROTOCOLS "LP45""DSM2""DSMX" #define LEN_MULTI_PROTOCOLS "\006" -#define TR_MULTI_PROTOCOLS "FlySky""Hubsan""FrSky\0""Hisky\0""V2x2\0 ""DSM\0 ""Devo\0 ""YD717\0""KN\0 ""SymaX\0""SLT\0 ""CX10\0 ""CG023\0""Bayang""ESky\0 ""MT99XX""MJXQ\0 ""Shenqi""FY326\0""SFHSS\0""J6 PRO""FQ777\0""Assan\0""Hontai""OLRS\0 ""FS 2A\0""Q2x2\0 ""Walk.\0""Q303\0 ""GW008\0""DM002\0" +#define TR_MULTI_PROTOCOLS "FlySky""Hubsan""FrSky\0""Hisky\0""V2x2\0 ""DSM\0 ""Devo\0 ""YD717\0""KN\0 ""SymaX\0""SLT\0 ""CX10\0 ""CG023\0""Bayang""ESky\0 ""MT99XX""MJXQ\0 ""Shenqi""FY326\0""SFHSS\0""J6 PRO""FQ777\0""Assan\0""Hontai""OLRS\0 ""FS 2A\0""Q2x2\0 ""Walk.\0""Q303\0 ""GW008\0""DM002\0""Cabell""Esky15""H8 3D\0" #define TR_MULTI_CUSTOM "Custom" @@ -431,9 +434,16 @@ #define LEN_GPSFORMAT "\004" #define TR_GPSFORMAT "HMS NMEA" -#define LEN2_VTEMPLATES 13 -#define LEN_VTEMPLATES "\015" -#define TR_VTEMPLATES "Clear Mixes\0\0""Simple 4-CH \0""Sticky-T-Cut\0""V-Tail \0""Elevon\\Delta\0""eCCPM \0""Heli Setup \0""Servo Test \0" +#define LEN2_VTEMPLATES 12 +#define LEN_VTEMPLATES "\014" +#define TR_TEMPLATE_CLEAR_MIXES "Clear Mixes " +#define TR_TEMPLATE_SIMPLE_4CH "Simple 4-CH " +#define TR_TEMPLATE_STICKY_TCUT "Sticky-T-Cut" +#define TR_TEMPLATE_VTAIL "V-Tail " +#define TR_TEMPLATE_DELTA "Elevon\\Delta" +#define TR_TEMPLATE_ECCPM "eCCPM " +#define TR_TEMPLATE_HELI "Heli Setup " +#define TR_TEMPLATE_SERVO_TEST "Servo Test " #define LEN_VSWASHTYPE "\004" #define TR_VSWASHTYPE "---\0""120\0""120X""140\0""90\0" @@ -544,7 +554,8 @@ #define TR_VTRAINER_SLAVE_JACK "Slave/Jack\0 " #define TR_VTRAINER_MASTER_SBUS_MODULE "Master/SBUS Module" #define TR_VTRAINER_MASTER_CPPM_MODULE "Master/CPPM Module" -#define TR_VTRAINER_MASTER_BATTERY "Master/Battery\0" +#define TR_VTRAINER_MASTER_BATTERY "Master/Battery\0 " +#define TR_VTRAINER_BLUETOOTH TR("Master/BT\0 ""Slave/BT\0", "Master/Bluetooth\0 ""Slave/Bluetooth\0 ") #define LEN_VFAILSAFE "\011" #define TR_VFAILSAFE "Not set\0 ""Hold\0 ""Custom\0 ""No pulses""Receiver\0" @@ -628,6 +639,8 @@ #endif #define TR_PROTO TR(INDENT "Proto", INDENT "Protocol") #define TR_PPMFRAME TR("PPM frame", INDENT "PPM frame") +#define TR_REFRESHRATE TR(INDENT "Refresh", INDENT "Refresh rate") +#define STR_WARN_BATTVOLTAGE TR(INDENT "Output is VBAT: ", INDENT "Warning: output level is VBAT: ") #define TR_MS "ms" #define TR_SWITCH "Switch" #define TR_TRIMS "Trims" @@ -690,6 +703,9 @@ #define TR_INACTIVITYALARM INDENT"Inactivity" #define TR_MEMORYWARNING INDENT"Memory Low" #define TR_ALARMWARNING INDENT"Sound Off" +#define TR_RSSISHUTDOWNALARM TR(INDENT "Rssi Shutdown", INDENT "Check Rssi on Shutdown") +#define TR_MODEL_STILL_POWERED "Model still powered" +#define TR_PRESS_ENTER_TO_CONFIRM "Press enter to confirm" #define TR_RENAVIG "RotEnc Navig" #define TR_THROTTLE_LABEL "Throttle" #define TR_THROTTLEREVERSE TR("T-Reverse", INDENT "Throttle reverse") @@ -820,17 +836,25 @@ #define TR_MULTI_AUTOBIND TR(INDENT "Autobind",INDENT "Bind on powerup") #define TR_MULTI_DSM_AUTODTECT TR(INDENT "Autodetect", INDENT "Autodetect format") #define TR_MULTI_LOWPOWER TR(INDENT "Low power", INDENT "Low power mode") +#define TR_MODULE_TELEMETRY TR(INDENT "Mod telem.", INDENT "Module telemetry") #define TR_DISABLE_INTERNAL TR("Disable int. RF", "Disable internal RF") #define TR_MODULE_NO_SERIAL_MODE TR("!serial mode", "Not in serial mode") #define TR_MODULE_NO_INPUT TR("No input", "No serial input") #define TR_MODULE_NO_TELEMETRY TR3( "No telmetry", "No MULTI_TELEMETRY", "No telemetry (enable MULTI_TELEMETRY)") +#define TR_MODULE_WAITFORBIND "Bind to load protocol" #define TR_MODULE_BINDING "Binding" -#define TR_BINDING_MODE1 "Ch1-8 Telem ON" -#define TR_BINDING_MODE2 "Ch1-8 Telem OFF" -#define TR_BINDING_MODE3 "Ch9-16 Telem ON" -#define TR_BINDING_MODE4 "Ch9-16 Telem OFF" +#define TR_BINDING_CH1_8_TELEM_ON "Ch1-8 Telem ON" +#define TR_BINDING_CH1_8_TELEM_OFF "Ch1-8 Telem OFF" +#define TR_BINDING_CH9_16_TELEM_ON "Ch9-16 Telem ON" +#define TR_BINDING_CH9_16_TELEM_OFF "Ch9-16 Telem OFF" +#define TR_BINDING_25MW_CH1_8_TELEM_OFF TR("25mW Ch1-8 Tel OFF", "25mW Ch1-8 Telem OFF") +#define TR_BINDING_25MW_CH1_8_TELEM_ON TR("25mW Ch1-8 Tel ON", "25mW Ch1-8 Telem ON") +#define TR_BINDING_500MW_CH1_8_TELEM_OFF TR("500mW Ch1-8 Tel OFF", "500mW Ch1-8 Telem OFF") +#define TR_BINDING_500MW_CH9_16_TELEM_OFF TR("500mW Ch9-16 Tel OFF", "500mW Ch9-16 Telem OFF") +#define TR_BINDING_OPTION "Set at bind" #define TR_PROTOCOL_INVALID TR("Prot. invalid", "Protocol invalid") #define TR_MODULE_STATUS TR(INDENT "Status", INDENT "Module Status") +#define TR_MODULE_SYNC TR(INDENT "Sync", INDENT "Module Sync") #define TR_MULTI_SERVOFREQ TR(INDENT "Servo rate", INDENT "Servo update rate") #define TR_SYNCMENU "[Sync]" #define TR_LIMIT INDENT"Limit" @@ -874,6 +898,8 @@ #define TR_ALARMSWARN "ALARMS" #define TR_SWITCHWARN TR("SWITCH","CONTROL") #define TR_FAILSAFEWARN "FAILSAFE" +#define TR_NIGHTLY_WARNING TR("NIGHTLY", "NIGHTLY BUILD") +#define TR_NIGHTLY_NOTSAFE "Version not safe to fly" #define TR_WRONG_SDCARDVERSION TR("Expected ver: ","Expected version: ") #define TR_WRONG_PCBREV "Wrong PCB detected" #define TR_EMERGENCY_MODE "EMERGENCY MODE" @@ -920,7 +946,13 @@ #define TR_FORMATTING "Formatting..." #define TR_TEMP_CALIB "Temp. Calib" #define TR_TIME "Time" +#define TR_MAXBAUDRATE "Max bauds" + +#define TR_BLUETOOTH "Bluetooth" #define TR_BAUDRATE "BT Baudrate" +#define LEN_BLUETOOTH_MODES "\011" +#define TR_BLUETOOTH_MODES "---\0 ""Telemetry""Trainer\0" + #define TR_SD_INFO_TITLE "SD INFO" #define TR_SD_TYPE "Type:" #define TR_SD_SPEED "Speed:" @@ -954,6 +986,7 @@ #define TR_MENUSENSOR "SENSOR" #define TR_SENSOR "SENSOR" #define TR_COUNTRYCODE "Country Code" +#define TR_USBMODE "USB Mode" #define TR_VOICELANG "Voice Language" #define TR_UNITSSYSTEM "Units" #define TR_EDIT "Edit" @@ -971,7 +1004,10 @@ #define TR_RESET_TELEMETRY "Reset Telemetry" #define TR_STATISTICS "Statistics" #define TR_ABOUT_US "About" -#define TR_SETUP_SCREENS "Setup screens" +#define TR_USB_JOYSTICK "USB Joystick (HID)" +#define TR_USB_MASS_STORAGE "USB Storage (SD)" +#define TR_USB_SERIAL "USB Serial (Debug)" +#define TR_SETUP_SCREENS "Setup screens" #define TR_MONITOR_SCREENS "Monitors" #define TR_AND_SWITCH "AND Switch" #define TR_SF "CF" @@ -985,7 +1021,7 @@ #define TR_SET "[Set]" #define TR_TRAINER "Trainer" #define TR_ANTENNAPROBLEM CENTER "TX Antenna problem!" -#define TR_MODELIDUSED TR("ID already used","Model ID already used") +#define TR_MODELIDUSED TR("ID used in:", "Receiver ID used in:") #define TR_MODULE INDENT "Module" #define TR_TELEMETRY_TYPE TR("Type", "Telemetry Type") #define TR_TELEMETRY_SENSORS "Sensors" @@ -999,6 +1035,9 @@ #define TR_ANTENNACONFIRM2 "Make sure antenna is installed!" #define TR_LOWALARM INDENT "Low Alarm" #define TR_CRITICALALARM INDENT "Critical Alarm" +#define TR_RSSIALARM_WARN TR("RSSI","TELEMETRY RSSI") +#define TR_NO_RSSIALARM TR(INDENT "Alarms disabled", INDENT "Telemetry alarms disabled") +#define TR_DISABLE_ALARM TR(INDENT "Disable alarms", INDENT "Disable telemetry alarms") #define TR_ENABLE_POPUP "Enable Popup" #define TR_DISABLE_POPUP "Disable Popup" #define TR_POPUP "Popup" diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/translations/fr.h.txt opentx-companion22-2.2.1~ppa01~xenial/radio/src/translations/fr.h.txt --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/translations/fr.h.txt 2017-05-31 19:49:19.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/translations/fr.h.txt 2017-12-17 16:22:27.000000000 +0000 @@ -43,127 +43,130 @@ // NON ZERO TERMINATED STRINGS -#define LEN_OFFON "\003" -#define TR_OFFON "OFF""ON\0" +#define LEN_OFFON "\003" +#define TR_OFFON "OFF""ON\0" -#define LEN_MMMINV "\003" -#define TR_MMMINV "---""INV" +#define LEN_MMMINV "\003" +#define TR_MMMINV "---""INV" -#define LEN_NCHANNELS "\004" -#define TR_NCHANNELS "\0014CH\0016CH\0018CH10CH12CH14CH16CH" +#define LEN_NCHANNELS "\004" +#define TR_NCHANNELS "\0014CH\0016CH\0018CH10CH12CH14CH16CH" -#define LEN_VBEEPMODE "\005" -#define TR_VBEEPMODE "Aucun""Alarm""NoKey""Tout\0" +#define LEN_VBEEPMODE "\005" +#define TR_VBEEPMODE "Aucun""Alarm""NoKey""Tout\0" -#define LEN_VBEEPLEN "\005" -#define TR_VBEEPLEN "0====""=0===""==0==""===0=""====0" +#define LEN_VBEEPLEN "\005" +#define TR_VBEEPLEN "0====""=0===""==0==""===0=""====0" -#define LEN_VRENAVIG "\003" -#define TR_VRENAVIG "NonREaREb" +#define LEN_VRENAVIG "\003" +#define TR_VRENAVIG "NonREaREb" -#define LEN_VBLMODE TR("\004", "\011") -#define TR_VBLMODE TR("OFF\0""Btns""Ctrl""Tous""ON\0","OFF\0 ""Touches\0 ""Controles""Tous\0 ""ON\0 ") +#define LEN_VBLMODE TR("\004", "\011") +#define TR_VBLMODE TR("OFF\0""Btns""Ctrl""Tous""ON\0","OFF\0 ""Touches\0 ""Controles""Tous\0 ""ON\0 ") -#define LEN_TRNMODE "\003" -#define TR_TRNMODE "OFF"" +="" :=" +#define LEN_TRNMODE "\003" +#define TR_TRNMODE "OFF"" +="" :=" -#define LEN_TRNCHN "\003" -#define TR_TRNCHN "CH1CH2CH3CH4" +#define LEN_TRNCHN "\003" +#define TR_TRNCHN "CH1CH2CH3CH4" -#define LEN_UART3MODES "\016" -#define TR_UART3MODES "OFF\0 ""Recopie S-Port""Télémétrie\0 ""Ecolage SBUS\0 ""Debug\0" +#define LEN_UART3MODES "\016" +#define TR_UART3MODES "OFF\0 ""Recopie S-Port""Télémétrie\0 ""Ecolage SBUS\0 ""Debug\0" -#define LEN_SWTYPES "\006" -#define TR_SWTYPES "Rien\0 ""Levier""2-POS\0""3-POS\0" +#define LEN_SWTYPES "\006" +#define TR_SWTYPES "Rien\0 ""Levier""2-POS\0""3-POS\0" -#define LEN_POTTYPES TR("\013","\017") -#define TR_POTTYPES TR("Rien\0 ""Pot av. ctr""Multipos\0 ""Pot\0 ", "Rien\0 ""Pot avec centre""Inter multi-pos""Potentiomètre\0") +#define LEN_POTTYPES TR("\013","\017") +#define TR_POTTYPES TR("Rien\0 ""Pot av. ctr""Multipos\0 ""Pot\0 ", "Rien\0 ""Pot avec centre""Inter multi-pos""Potentiomètre\0") -#define LEN_SLIDERTYPES "\006" -#define TR_SLIDERTYPES "Rien\0 ""Slider" +#define LEN_SLIDERTYPES "\006" +#define TR_SLIDERTYPES "Rien\0 ""Slider" -#define LEN_DATETIME "\005" -#define TR_DATETIME "DATE:""HEURE" +#define LEN_DATETIME "\005" +#define TR_DATETIME "DATE:""HEURE" -#define LEN_VLCD "\006" -#define TR_VLCD "NormalOptrex" +#define LEN_VLCD "\006" +#define TR_VLCD "NormalOptrex" -#define LEN_VPERSISTENT "\014" -#define TR_VPERSISTENT "OFF\0 ""Vol\0 ""Reset Manuel" +#define LEN_VPERSISTENT "\014" +#define TR_VPERSISTENT "OFF\0 ""Vol\0 ""Reset Manuel" -#define LEN_COUNTRYCODES TR("\002", "\006") -#define TR_COUNTRYCODES TR("US""JP""EU", "USA\0 ""Japon\0""Europe") +#define LEN_COUNTRYCODES TR("\002", "\006") +#define TR_COUNTRYCODES TR("US""JP""EU", "USA\0 ""Japon\0""Europe") -#define LEN_TARANIS_PROTOCOLS "\004" -#define TR_TARANIS_PROTOCOLS "OFF\0""PPM\0""XJT\0""DSM2""CRSF""MULT" +#define LEN_USBMODES TR("\006", "\010") +#define TR_USBMODES TR("Popup\0""Joyst\0""SDCard""Série\0", "Demander""Joystick""Stockage""Série\0 ") -#define LEN_TELEMETRY_PROTOCOLS "\017" -#define TR_TELEMETRY_PROTOCOLS "FrSky S.PORT\0 ""FrSky D\0 ""FrSky D (cable)""TBS Crossfire\0 ""Spektrum\0 ""AFHDS2A IBUS\0 ""Multi Telemetry" +#define LEN_TARANIS_PROTOCOLS "\004" +#define TR_TARANIS_PROTOCOLS "OFF\0""PPM\0""XJT\0""DSM2""CRSF""MULT""R9M\0""SBUS" -#define LEN_XJT_PROTOCOLS "\004" -#define TR_XJT_PROTOCOLS "OFF\0""D16\0""D8\0 ""LR12" +#define LEN_TELEMETRY_PROTOCOLS "\017" +#define TR_TELEMETRY_PROTOCOLS "FrSky S.PORT\0 ""FrSky D\0 ""FrSky D (cable)""TBS Crossfire\0 ""Spektrum\0 ""AFHDS2A IBUS\0 ""Multi Telemetry" -#define LEN_DSM_PROTOCOLS "\004" -#define TR_DSM_PROTOCOLS "LP45""DSM2""DSMX" +#define LEN_XJT_PROTOCOLS "\004" +#define TR_XJT_PROTOCOLS "OFF\0""D16\0""D8\0 ""LR12" -#define LEN_MULTI_PROTOCOLS "\006" -#define TR_MULTI_PROTOCOLS "FlySky""Hubsan""FrSky\0""Hisky\0""V2x2\0 ""DSM\0 ""Devo\0 ""YD717\0""KN\0 ""SymaX\0""SLT\0 ""CX10\0 ""CG023\0""Bayang""ESky\0 ""MT99XX""MJXQ\0 ""Shenqi""FY326\0""SFHSS\0""J6 PRO""FQ777\0""Assan\0""Hontai""OLRS\0 ""FS 2A\0""Q2x2\0 ""Walk.\0""Q303\0 ""GW008\0""DM002\0" +#define LEN_DSM_PROTOCOLS "\004" +#define TR_DSM_PROTOCOLS "LP45""DSM2""DSMX" -#define TR_MULTI_CUSTOM "Perso" +#define LEN_MULTI_PROTOCOLS "\006" +#define TR_MULTI_PROTOCOLS "FlySky""Hubsan""FrSky\0""Hisky\0""V2x2\0 ""DSM\0 ""Devo\0 ""YD717\0""KN\0 ""SymaX\0""SLT\0 ""CX10\0 ""CG023\0""Bayang""ESky\0 ""MT99XX""MJXQ\0 ""Shenqi""FY326\0""SFHSS\0""J6 PRO""FQ777\0""Assan\0""Hontai""OLRS\0 ""FS 2A\0""Q2x2\0 ""Walk.\0""Q303\0 ""GW008\0""DM002\0""Cabell""Esky15""H8 3D\0" -#define LEN_VTRIMINC TR("\006", "\013") -#define TR_VTRIMINC TR("Expo\0 ""ExFin\0""Fin\0 ""Moyen\0""Gros\0 ","Exponentiel""Extra Fin\0 ""Fin\0 ""Moyen\0 ""Grossier\0 ") +#define TR_MULTI_CUSTOM "Perso" -#define LEN_VDISPLAYTRIMS "\006" -#define TR_VDISPLAYTRIMS "Non\0 ""Change""Oui\0" +#define LEN_VTRIMINC TR("\006", "\013") +#define TR_VTRIMINC TR("Expo\0 ""ExFin\0""Fin\0 ""Moyen\0""Gros\0 ","Exponentiel""Extra Fin\0 ""Fin\0 ""Moyen\0 ""Grossier\0 ") -#define LEN_VBEEPCOUNTDOWN "\007" -#define TR_VBEEPCOUNTDOWN "Aucun\0 ""Bips\0 ""Voix\0 Haptic\0" +#define LEN_VDISPLAYTRIMS "\006" +#define TR_VDISPLAYTRIMS "Non\0 ""Change""Oui\0" -#define LEN_VVARIOCENTER "\006" -#define TR_VVARIOCENTER "Tone\0 ""Silent" +#define LEN_VBEEPCOUNTDOWN "\007" +#define TR_VBEEPCOUNTDOWN "Aucun\0 ""Bips\0 ""Voix\0 Haptic\0" -#define LEN_CURVE_TYPES "\010" -#define TR_CURVE_TYPES "Standard""Libre\0" +#define LEN_VVARIOCENTER "\006" +#define TR_VVARIOCENTER "Tone\0 ""Silent" -#define LEN_RETA123 "\001" +#define LEN_CURVE_TYPES "\010" +#define TR_CURVE_TYPES "Standard""Libre\0" + +#define LEN_RETA123 "\001" #if defined(PCBHORUS) - #define TR_RETA123 "DPGA12345LR" + #define TR_RETA123 "DPGA12345LR" #elif defined(PCBFLAMENCO) - #define TR_RETA123 "DPGA123LR" + #define TR_RETA123 "DPGA123LR" #elif defined(PCBX9E) - #define TR_RETA123 "DPGA1234LRLR" + #define TR_RETA123 "DPGA1234LRLR" #elif defined(PCBTARANIS) || defined(REVX) - #define TR_RETA123 "DPGA123LR" + #define TR_RETA123 "DPGA123LR" #elif defined(PCBSKY9X) - #define TR_RETA123 "DPGA123a" + #define TR_RETA123 "DPGA123a" #elif defined(CPUM2560) - #define TR_RETA123 "DPGA123ab" + #define TR_RETA123 "DPGA123ab" #else - #define TR_RETA123 "DPGA123" + #define TR_RETA123 "DPGA123" #endif -#define LEN_VPROTOS "\006" +#define LEN_VPROTOS "\006" #if defined(PXX) - #define TR_PXX "PXX\0 " + #define TR_PXX "PXX\0 " #elif defined(DSM2) || defined(IRPROTOS) - #define TR_PXX "[PXX]\0" + #define TR_PXX "[PXX]\0" #else #define TR_PXX #endif #if defined(DSM2) - #define TR_DSM2 "LP45\0 ""DSM2\0 ""DSMX\0 " + #define TR_DSM2 "LP45\0 ""DSM2\0 ""DSMX\0 " #elif defined(IRPROTOS) - #define TR_DSM2 "[LP45]""[DSM2]""[DSMX]" + #define TR_DSM2 "[LP45]""[DSM2]""[DSMX]" #else #define TR_DSM2 #endif #if defined(IRPROTOS) - #define TR_IRPROTOS "SLV TRAC09PICZ SWIFT\0" + #define TR_IRPROTOS "SLV TRAC09PICZ SWIFT\0" #else #define TR_IRPROTOS #endif @@ -171,47 +174,47 @@ #if defined(CPUARM) #define TR_XPPM #else - #define TR_XPPM "PPM16\0""PPMsim" + #define TR_XPPM "PPM16\0""PPMsim" #endif -#define TR_VPROTOS "PPM\0 " TR_XPPM TR_PXX TR_DSM2 TR_IRPROTOS +#define TR_VPROTOS "PPM\0 " TR_XPPM TR_PXX TR_DSM2 TR_IRPROTOS -#define LEN_POSNEG "\003" -#define TR_POSNEG "POS""NEG" +#define LEN_POSNEG "\003" +#define TR_POSNEG "POS""NEG" #if defined(PCBSKY9X) && defined(REVX) - #define LEN_VOUTPUT_TYPE "\011" - #define TR_VOUTPUT_TYPE "OpenDrain""PushPull\0" + #define LEN_VOUTPUT_TYPE "\011" + #define TR_VOUTPUT_TYPE "OpenDrain""PushPull\0" #endif -#define LEN_VCURVEFUNC "\003" -#define TR_VCURVEFUNC "---""x>0""x<0""|x|""f>0""f<0""|f|" +#define LEN_VCURVEFUNC "\003" +#define TR_VCURVEFUNC "---""x>0""x<0""|x|""f>0""f<0""|f|" -#define LEN_VMLTPX TR("\010", "\013") -#define TR_VMLTPX TR("Ajoute\0 ""Multipl.""Remplace", "Additionner""Multiplier\0""Remplacer\0") +#define LEN_VMLTPX TR("\010", "\013") +#define TR_VMLTPX TR("Ajoute\0 ""Multipl.""Remplace", "Additionner""Multiplier\0""Remplacer\0") -#define LEN_VMLTPX2 "\002" -#define TR_VMLTPX2 "+=""*="":=" +#define LEN_VMLTPX2 "\002" +#define TR_VMLTPX2 "+=""*="":=" -#define LEN_VMIXTRIMS "\003" +#define LEN_VMIXTRIMS "\003" #if defined(PCBHORUS) - #define TR_VMIXTRIMS "OFF""ON\0""Dir""Prf""Gaz""Ail""T5\0""T6\0" + #define TR_VMIXTRIMS "OFF""ON\0""Dir""Prf""Gaz""Ail""T5\0""T6\0" #else - #define TR_VMIXTRIMS "OFF""ON\0""Dir""Prf""Gaz""Ail" + #define TR_VMIXTRIMS "OFF""ON\0""Dir""Prf""Gaz""Ail" #endif #if LCD_W >= 212 - #define TR_CSWTIMER "Tempo" - #define TR_CSWSTICKY "Bistb" - #define TR_CSWRANGE "Plage" - #define TR_CSWSTAY "Flanc" + #define TR_CSWTIMER "Tempo" + #define TR_CSWSTICKY "Bistb" + #define TR_CSWRANGE "Plage" + #define TR_CSWSTAY "Flanc" #else - #define TR_CSWTIMER "Temp\0" - #define TR_CSWSTICKY "Bist\0" + #define TR_CSWTIMER "Temp\0" + #define TR_CSWSTICKY "Bist\0" #if defined(CPUARM) - #define TR_CSWRANGE "Zone\0" - #define TR_CSWSTAY "Flnc\0" + #define TR_CSWRANGE "Zone\0" + #define TR_CSWSTAY "Flnc\0" #else #define TR_CSWRANGE #define TR_CSWSTAY @@ -219,140 +222,140 @@ #endif #if defined(CPUARM) - #define TR_CSWEQUAL "a=x\0 " + #define TR_CSWEQUAL "a=x\0 " #else #define TR_CSWEQUAL #endif -#define LEN_VCSWFUNC "\005" +#define LEN_VCSWFUNC "\005" #if defined(CPUARM) -#define TR_VCSWFUNC "---\0 " TR_CSWEQUAL "a~x\0 ""a>x\0 ""ax""|a|b\0 ""ax\0 ""ax""|a|b\0 ""ax\0 ""ax""|a|b\0 ""ax\0 ""ax""|a|b\0 ""a= 212 - #define TR_SF_SAFETY "Remplace\0 " + #define TR_SF_SAFETY "Remplace\0 " #elif defined(OVERRIDE_CHANNEL_FUNCTION) - #define TR_SF_SAFETY "Rempl.\0 " + #define TR_SF_SAFETY "Rempl.\0 " #else - #define TR_SF_SAFETY "---\0 " + #define TR_SF_SAFETY "---\0 " #endif #if defined(PCBTARANIS) - #define TR_SF_SCREENSHOT "Photo Ecran\0 " + #define TR_SF_SCREENSHOT "Photo Ecran\0 " #else #define TR_SF_SCREENSHOT #endif -#define TR_SF_RESERVE "[reserve]\0 " +#define TR_SF_RESERVE "[reserve]\0 " #if defined(CPUARM) - #define TR_VFSWFUNC TR_SF_SAFETY "Ecolage\0 ""Trim instant.""Remise à 0\0 ""Déf.\0 " TR_ADJUST_GVAR "Volume\0 " "DéfFailsafe\0 " "Test Port.\0 " "Bind\0 " TR_SOUND TR_PLAY_TRACK TR_PLAY_VALUE TR_SF_RESERVE TR_SF_PLAY_SCRIPT TR_SF_RESERVE TR_SF_BG_MUSIC TR_VVARIO TR_HAPTIC TR_SDCLOGS "Rétroécl.\0 " TR_SF_SCREENSHOT TR_SF_TEST + #define TR_VFSWFUNC TR_SF_SAFETY "Ecolage\0 ""Trim instant.""Remise à 0\0 ""Déf.\0 " TR_ADJUST_GVAR "Volume\0 " "DéfFailsafe\0 " "Test Port.\0 " "Bind\0 " TR_SOUND TR_PLAY_TRACK TR_PLAY_VALUE TR_SF_RESERVE TR_SF_PLAY_SCRIPT TR_SF_RESERVE TR_SF_BG_MUSIC TR_VVARIO TR_HAPTIC TR_SDCLOGS "Rétroécl.\0 " TR_SF_SCREENSHOT TR_SF_TEST #elif defined(PCBGRUVIN9X) - #define TR_VFSWFUNC TR_SF_SAFETY "Ecolage\0 ""Trim instant.""Remise à 0\0 " TR_ADJUST_GVAR TR_SOUND TR_PLAY_TRACK TR_PLAY_BOTH TR_PLAY_VALUE TR_VVARIO TR_HAPTIC TR_SDCLOGS "Rétroécl.\0 " TR_SF_TEST + #define TR_VFSWFUNC TR_SF_SAFETY "Ecolage\0 ""Trim instant.""Remise à 0\0 " TR_ADJUST_GVAR TR_SOUND TR_PLAY_TRACK TR_PLAY_BOTH TR_PLAY_VALUE TR_VVARIO TR_HAPTIC TR_SDCLOGS "Rétroécl.\0 " TR_SF_TEST #else - #define TR_VFSWFUNC TR_SF_SAFETY "Ecolage\0 ""Trim instant.""Remise à 0\0 " TR_ADJUST_GVAR TR_SOUND TR_PLAY_TRACK TR_PLAY_BOTH TR_PLAY_VALUE TR_VVARIO TR_HAPTIC "Rétroécl.\0 " TR_SF_TEST + #define TR_VFSWFUNC TR_SF_SAFETY "Ecolage\0 ""Trim instant.""Remise à 0\0 " TR_ADJUST_GVAR TR_SOUND TR_PLAY_TRACK TR_PLAY_BOTH TR_PLAY_VALUE TR_VVARIO TR_HAPTIC "Rétroécl.\0 " TR_SF_TEST #endif -#define LEN_VFSWRESET TR("\004", "\012") +#define LEN_VFSWRESET TR("\004", "\012") #if defined(TELEMETRY_FRSKY) - #define TR_FSW_RESET_TELEM TR("Télm", "Télémesure") + #define TR_FSW_RESET_TELEM TR("Télm", "Télémétrie") #else #define TR_FSW_RESET_TELEM #endif #if ROTARY_ENCODERS == 2 - #define TR_FSW_RESET_ROTENC TR("ERa\0""ERb\0", "Enc.Rot.A\0""Enc.Rot.B\0") + #define TR_FSW_RESET_ROTENC TR("ERa\0""ERb\0", "Enc.Rot.A\0""Enc.Rot.B\0") #elif ROTARY_ENCODERS == 1 - #define TR_FSW_RESET_ROTENC TR("EncR", "Enc.Rot\0 ") + #define TR_FSW_RESET_ROTENC TR("EncR", "Enc.Rot\0 ") #else #define TR_FSW_RESET_ROTENC #endif #if LCD_W >= 212 - #define TR_FSW_RESET_TIMERS "Chrono 1\0 ""Chrono 2\0 ""Chrono 3\0 " + #define TR_FSW_RESET_TIMERS "Chrono 1\0 ""Chrono 2\0 ""Chrono 3\0 " #elif defined(CPUARM) - #define TR_FSW_RESET_TIMERS "Chr1""Chr2""Chr3" + #define TR_FSW_RESET_TIMERS "Chr1""Chr2""Chr3" #else - #define TR_FSW_RESET_TIMERS "Chr1""Chr2" + #define TR_FSW_RESET_TIMERS "Chr1""Chr2" #endif -#define TR_VFSWRESET TR(TR_FSW_RESET_TIMERS "Tout" TR_FSW_RESET_TELEM TR_FSW_RESET_ROTENC, TR_FSW_RESET_TIMERS "Tout\0 " TR_FSW_RESET_TELEM TR_FSW_RESET_ROTENC) +#define TR_VFSWRESET TR(TR_FSW_RESET_TIMERS "Tout" TR_FSW_RESET_TELEM TR_FSW_RESET_ROTENC, TR_FSW_RESET_TIMERS "Tout\0 " TR_FSW_RESET_TELEM TR_FSW_RESET_ROTENC) -#define LEN_FUNCSOUNDS TR("\004", "\006") -#define TR_FUNCSOUNDS TR("Bp1\0""Bp2\0""Bp3\0""Wrn1""Wrn2""Chee""Rata""Tick""Sirn""Ring""SciF""Robt""Chrp""Tada""Crck""Alrm", "Beep1 ""Beep2 ""Beep3 ""Warn1 ""Warn2 ""Cheep ""Ratata""Tick ""Siren ""Ring ""SciFi ""Robot ""Chirp ""Tada ""Crickt""AlmClk") +#define LEN_FUNCSOUNDS TR("\004", "\006") +#define TR_FUNCSOUNDS TR("Bp1\0""Bp2\0""Bp3\0""Wrn1""Wrn2""Chee""Rata""Tick""Sirn""Ring""SciF""Robt""Chrp""Tada""Crck""Alrm", "Beep1 ""Beep2 ""Beep3 ""Warn1 ""Warn2 ""Cheep ""Ratata""Tick ""Siren ""Ring ""SciFi ""Robot ""Chirp ""Tada ""Crickt""AlmClk") -#define LEN_VTELEMCHNS "\004" +#define LEN_VTELEMCHNS "\004" #if defined(CPUARM) - #define TR_TELEM_RESERVE TR("[--]", "[---]") - #define TR_TELEM_TIME TR("Heur", "H:M\0 ") - #define TR_SWR TR("SWR\0", "SWR\0 ") - #define TR_RX_BATT TR("BtRx", "BatRx") - #define TR_A3_A4 TR("A3\0 ""A4\0 ", "A3\0 ""A4\0 ") - #define TR_A3_A4_MIN TR("A3-\0""A4-\0", "A3-\0 ""A4-\0 ") + #define TR_TELEM_RESERVE TR("[--]", "[---]") + #define TR_TELEM_TIME TR("Heur", "H:M\0 ") + #define TR_SWR TR("SWR\0", "SWR\0 ") + #define TR_RX_BATT TR("BtRx", "BatRx") + #define TR_A3_A4 TR("A3\0 ""A4\0 ", "A3\0 ""A4\0 ") + #define TR_A3_A4_MIN TR("A3-\0""A4-\0", "A3-\0 ""A4-\0 ") #else #define TR_TELEM_RESERVE #define TR_TELEM_TIME @@ -362,703 +365,745 @@ #define TR_A3_A4_MIN #endif -#define TR_ASPD_MAX TR("ViA+", "VitA+") +#define TR_ASPD_MAX TR("ViA+", "VitA+") #if LCD_W >= 212 - #define TR_TELEM_RSSI_RX "RSSI\0" + #define TR_TELEM_RSSI_RX "RSSI\0" #else - #define TR_TELEM_RSSI_RX TR("Rx\0 ", "Rx\0 ") + #define TR_TELEM_RSSI_RX TR("Rx\0 ", "Rx\0 ") #endif #if defined(CPUARM) - #define TR_TELEM_TIMERS TR("Chr1""Chr2""Chr3", "Chr1\0""Chr2\0""Chr3\0") + #define TR_TELEM_TIMERS TR("Chr1""Chr2""Chr3", "Chr1\0""Chr2\0""Chr3\0") #else - #define TR_TELEM_TIMERS TR("Chr1""Chr2", "Chr1\0""Chr2\0") + #define TR_TELEM_TIMERS TR("Chr1""Chr2", "Chr1\0""Chr2\0") #endif -#define LENGTH_UNIT_IMP "ft\0" -#define SPEED_UNIT_IMP "mph" -#define LENGTH_UNIT_METR "m\0 " -#define SPEED_UNIT_METR "kmh" +#define LENGTH_UNIT_IMP "ft\0" +#define SPEED_UNIT_IMP "mph" +#define LENGTH_UNIT_METR "m\0 " +#define SPEED_UNIT_METR "kmh" #if defined(CPUARM) - #define LEN_VUNITSSYSTEM TR("\006", "\012") - #define TR_VUNITSSYSTEM TR("Métr.\0""Impér.", "Métriques\0""Impériales") - #define LEN_VTELEMUNIT "\003" - #define TR_VTELEMUNIT "-\0 ""V\0 ""A\0 ""mA\0""kts""m/s""f/s""kmh""mph""m\0 ""ft\0""@C\0""@F\0""%\0 ""mAh""W\0 ""mW\0""dB\0""rpm""g\0 ""@\0 ""rad""ml\0""fOz" + #define LEN_VUNITSSYSTEM TR("\006", "\012") + #define TR_VUNITSSYSTEM TR("Métr.\0""Impér.", "Métriques\0""Impériales") + #define LEN_VTELEMUNIT "\003" + #define TR_VTELEMUNIT "-\0 ""V\0 ""A\0 ""mA\0""kts""m/s""f/s""kmh""mph""m\0 ""ft\0""@C\0""@F\0""%\0 ""mAh""W\0 ""mW\0""dB\0""rpm""g\0 ""@\0 ""rad""ml\0""fOz" #else #if defined(IMPERIAL_UNITS) - #define LENGTH_UNIT LENGTH_UNIT_IMP - #define SPEED_UNIT SPEED_UNIT_IMP + #define LENGTH_UNIT LENGTH_UNIT_IMP + #define SPEED_UNIT SPEED_UNIT_IMP #else - #define LENGTH_UNIT LENGTH_UNIT_METR - #define SPEED_UNIT SPEED_UNIT_METR + #define LENGTH_UNIT LENGTH_UNIT_METR + #define SPEED_UNIT SPEED_UNIT_METR #endif - #define LEN_VTELEMUNIT "\003" - #define TR_VTELEMUNIT "V\0 ""A\0 ""m/s""-\0 " SPEED_UNIT LENGTH_UNIT "@\0 ""%\0 ""mA\0""mAh""W\0 " + #define LEN_VTELEMUNIT "\003" + #define TR_VTELEMUNIT "V\0 ""A\0 ""m/s""-\0 " SPEED_UNIT LENGTH_UNIT "@\0 ""%\0 ""mA\0""mAh""W\0 " #endif -#define STR_V (STR_VTELEMUNIT+1) -#define STR_A (STR_VTELEMUNIT+4) +#define STR_V (STR_VTELEMUNIT+1) +#define STR_A (STR_VTELEMUNIT+4) -#define LEN_VALARM "\004" -#define TR_VALARM "----""Jaun""Oran""Roug" +#define LEN_VALARM "\004" +#define TR_VALARM "----""Jaun""Oran""Roug" -#define LEN_VALARMFN "\001" -#define TR_VALARMFN "<>" +#define LEN_VALARMFN "\001" +#define TR_VALARMFN "<>" -#define LEN_VTELPROTO "\007" -#define TR_VTELPROTO "Aucun ""Hub\0 ""WSHHigh" +#define LEN_VTELPROTO "\007" +#define TR_VTELPROTO "Aucun ""Hub\0 ""WSHHigh" #if defined(CPUARM) - #define LEN_AMPSRC TR("\003", "\005") - #define TR_AMPSRC TR("---""A1\0""A2\0""A3\0""A4\0""FAS""Cel", "---\0 ""A1\0 ""A2\0 ""A3\0 ""A4\0 ""FAS\0 ""Elem.") - #define LEN_VOLTSRC TR("\003", "\005") - #define TR_VOLTSRC TR("A1\0""A2\0""A3\0""A4\0""FAS""Cel", "A1\0 ""A2\0 ""A3\0 ""A4\0 ""FAS\0 ""Elem.") + #define LEN_AMPSRC TR("\003", "\005") + #define TR_AMPSRC TR("---""A1\0""A2\0""A3\0""A4\0""FAS""Cel", "---\0 ""A1\0 ""A2\0 ""A3\0 ""A4\0 ""FAS\0 ""Elem.") + #define LEN_VOLTSRC TR("\003", "\005") + #define TR_VOLTSRC TR("A1\0""A2\0""A3\0""A4\0""FAS""Cel", "A1\0 ""A2\0 ""A3\0 ""A4\0 ""FAS\0 ""Elem.") #else - #define LEN_AMPSRC TR("\003", "\005") - #define TR_AMPSRC TR("---""A1\0""A2\0""FAS""Cel", "---\0 ""A1\0 ""A2\0 ""FAS\0 ""Elem.") + #define LEN_AMPSRC TR("\003", "\005") + #define TR_AMPSRC TR("---""A1\0""A2\0""FAS""Cel", "---\0 ""A1\0 ""A2\0 ""FAS\0 ""Elem.") #endif -#define LEN_VARIOSRC "\005" +#define LEN_VARIOSRC "\005" #if defined(TELEMETRY_FRSKY_SPORT) - #define TR_VARIOSRC "Vario""A1\0 ""A2\0 ""dTE\0 " + #define TR_VARIOSRC "Vario""A1\0 ""A2\0 ""dTE\0 " #else - #define TR_VARIOSRC "Alti\0""Alti+""Vario""A1\0 ""A2\0" + #define TR_VARIOSRC "Alti\0""Alti+""Vario""A1\0 ""A2\0" #endif #if defined(CPUARM) - #define LEN_VTELEMSCREENTYPE "\007" - #define TR_VTELEMSCREENTYPE "Rien\0 ""Valeurs""Barres\0""Script\0" + #define LEN_VTELEMSCREENTYPE "\007" + #define TR_VTELEMSCREENTYPE "Rien\0 ""Valeurs""Barres\0""Script\0" #else - #define LEN_VTELEMSCREENTYPE "\004" - #define TR_VTELEMSCREENTYPE "Val.""Bars" + #define LEN_VTELEMSCREENTYPE "\004" + #define TR_VTELEMSCREENTYPE "Val.""Bars" #endif -#define LEN_GPSFORMAT "\004" -#define TR_GPSFORMAT "DMS\0""NMEA" - -#define LEN2_VTEMPLATES 15 -#define LEN_VTEMPLATES "\017" -#define TR_VTEMPLATES "Suppr Mixages\0 ""4 Voies simple\0""Coupure Gaz\0 ""Empennage V\0 ""Elevon\\Delta\0 ""eCCPM\0 ""Conf. Hélico\0 ""Test Servo\0 " +#define LEN_GPSFORMAT "\004" +#define TR_GPSFORMAT "DMS\0""NMEA" + +#define LEN2_VTEMPLATES 14 +#define LEN_VTEMPLATES "\016" +#define TR_TEMPLATE_CLEAR_MIXES "Suppr mixages\0" +#define TR_TEMPLATE_SIMPLE_4CH "4 voies simple" +#define TR_TEMPLATE_STICKY_TCUT "Coupure gaz\0 " +#define TR_TEMPLATE_VTAIL "Empennage V\0 " +#define TR_TEMPLATE_DELTA "Elevon\\Delta\0 " +#define TR_TEMPLATE_ECCPM "eCCPM\0 " +#define TR_TEMPLATE_HELI "Conf. Hélico\0 " +#define TR_TEMPLATE_SERVO_TEST "Test Servo\0 " -#define LEN_VSWASHTYPE "\004" -#define TR_VSWASHTYPE "--- ""120 ""120X""140 ""90\0" +#define LEN_VSWASHTYPE "\004" +#define TR_VSWASHTYPE "--- ""120 ""120X""140 ""90\0" -#define LEN_VKEYS "\005" -#define TR_VKEYS TR("Menu\0""Exit\0""Bas\0 ""Haut\0""Droit""Gauch", "Menu\0""Exit\0""Enter""Page\0""Plus\0""Minus") +#if defined(PCBHORUS) +#define LEN_VKEYS "\006" +#define TR_VKEYS "Menu\0 ""Exit\0 ""Entree""Haut\0 ""Bas\0 ""Droit\0""Gauche" +#elif defined(PCBTARANIS) +#define LEN_VKEYS "\005" +#define TR_VKEYS "Menu\0""Exit\0""Enter""Page\0""Plus\0""Moins" +#else +#define LEN_VKEYS "\005" +#define TR_VKEYS "Menu\0""Exit\0""Bas\0 ""Haut\0""Droit""Gauch" +#endif -#define LEN_VRENCODERS "\003" -#define TR_VRENCODERS "REa""REb" +#define LEN_VRENCODERS "\003" +#define TR_VRENCODERS "REa""REb" -#define LEN_VSWITCHES "\003" -#define LEN_VSRCRAW "\004" +#define LEN_VSWITCHES "\003" +#define LEN_VSRCRAW "\004" #if defined(CPUARM) -#define TR_STICKS_VSRCRAW "\307Dir""\307Prf""\307Gaz""\307Ail" +#define TR_STICKS_VSRCRAW "\307Dir""\307Prf""\307Gaz""\307Ail" #else -#define TR_STICKS_VSRCRAW "Dir\0""Prf\0""Gaz\0""Ail\0" +#define TR_STICKS_VSRCRAW "Dir\0""Prf\0""Gaz\0""Ail\0" #endif #if defined(PCBHORUS) - #define TR_TRIMS_VSRCRAW "\313Dir""\313Prf""\313Gaz""\313Ail""\313T5\0""\313T6\0" + #define TR_TRIMS_VSRCRAW "\313Dir""\313Prf""\313Gaz""\313Ail""\313T5\0""\313T6\0" #elif defined(CPUARM) - #define TR_TRIMS_VSRCRAW "\313Dir""\313Prf""\313Gaz""\313Ail" + #define TR_TRIMS_VSRCRAW "\313Dir""\313Prf""\313Gaz""\313Ail" #else - #define TR_TRIMS_VSRCRAW "TrmD""TrmP""TrmG""TrmA" + #define TR_TRIMS_VSRCRAW "TrmD""TrmP""TrmG""TrmA" #endif #if defined(PCBHORUS) - #define TR_POTS_VSRCRAW "\310S1\0""\3106P\0""\310S2\0""\313L1\0""\313L2\0""\311LS\0""\311RS\0""\310JSx""\310JSy" - #define TR_SW_VSRCRAW "\312SA\0""\312SB\0""\312SC\0""\312SD\0""\312SE\0""\312SF\0""\312SG\0""\312SH\0" + #define TR_POTS_VSRCRAW "\310S1\0""\3106P\0""\310S2\0""\313L1\0""\313L2\0""\311LS\0""\311RS\0""\310JSx""\310JSy" + #define TR_SW_VSRCRAW "\312SA\0""\312SB\0""\312SC\0""\312SD\0""\312SE\0""\312SF\0""\312SG\0""\312SH\0" #elif defined(PCBFLAMENCO) - #define TR_POTS_VSRCRAW "SD\0 ""LS\0 ""RS\0 " - #define TR_SW_VSRCRAW "SA\0 ""SB\0 ""SC\0 ""SE\0 ""SF\0 " + #define TR_POTS_VSRCRAW "SD\0 ""LS\0 ""RS\0 " + #define TR_SW_VSRCRAW "SA\0 ""SB\0 ""SC\0 ""SE\0 ""SF\0 " #elif defined(PCBX9E) - #define TR_POTS_VSRCRAW "\310F1\0""\310F2\0""\310F3\0""\310F4\0""\311S1\0""\311S2\0""\311LS\0""\311RS\0" - #define TR_SW_VSRCRAW "\312SA\0""\312SB\0""\312SC\0""\312SD\0""\312SE\0""\312SF\0""\312SG\0""\312SH\0""\312SI\0""\312SJ\0""\312SK\0""\312SL\0""\312SM\0""\312SN\0""\312SO\0""\312SP\0""\312SQ\0""\312SR\0" + #define TR_POTS_VSRCRAW "\310F1\0""\310F2\0""\310F3\0""\310F4\0""\311S1\0""\311S2\0""\311LS\0""\311RS\0" + #define TR_SW_VSRCRAW "\312SA\0""\312SB\0""\312SC\0""\312SD\0""\312SE\0""\312SF\0""\312SG\0""\312SH\0""\312SI\0""\312SJ\0""\312SK\0""\312SL\0""\312SM\0""\312SN\0""\312SO\0""\312SP\0""\312SQ\0""\312SR\0" #elif defined(PCBX7) - #define TR_POTS_VSRCRAW "\310S1\0""\310S2\0" - #define TR_SW_VSRCRAW "\312SA\0""\312SB\0""\312SC\0""\312SD\0""\312SF\0""\312SH\0" + #define TR_POTS_VSRCRAW "\310S1\0""\310S2\0" + #define TR_SW_VSRCRAW "\312SA\0""\312SB\0""\312SC\0""\312SD\0""\312SF\0""\312SH\0" #elif defined(PCBTARANIS) - #define TR_POTS_VSRCRAW "\310S1\0""\310S2\0""\310S3\0""\311LS\0""\311RS\0" - #define TR_SW_VSRCRAW "\312SA\0""\312SB\0""\312SC\0""\312SD\0""\312SE\0""\312SF\0""\312SG\0""\312SH\0" + #define TR_POTS_VSRCRAW "\310S1\0""\310S2\0""\310S3\0""\311LS\0""\311RS\0" + #define TR_SW_VSRCRAW "\312SA\0""\312SB\0""\312SC\0""\312SD\0""\312SE\0""\312SF\0""\312SG\0""\312SH\0" #elif defined(PCBSKY9X) - #define TR_POTS_VSRCRAW "P1\0 ""P2\0 ""P3\0 " - #define TR_SW_VSRCRAW "3POS" "THR\0""RUD\0""ELE\0""AIL\0""GEA\0""TRN\0" - #define TR_9X_3POS_SWITCHES "ID0""ID1""ID2" -#else - #define TR_POTS_VSRCRAW "P1\0 ""P2\0 ""P3\0 " - #define TR_SW_VSRCRAW "3POS" - #define TR_9X_3POS_SWITCHES "ID0""ID1""ID2" + #define TR_POTS_VSRCRAW "P1\0 ""P2\0 ""P3\0 " + #define TR_SW_VSRCRAW "3POS" "THR\0""RUD\0""ELE\0""AIL\0""GEA\0""TRN\0" + #define TR_9X_3POS_SWITCHES "ID0""ID1""ID2" +#else + #define TR_POTS_VSRCRAW "P1\0 ""P2\0 ""P3\0 " + #define TR_SW_VSRCRAW "3POS" + #define TR_9X_3POS_SWITCHES "ID0""ID1""ID2" #endif #if defined(CPUARM) - #define TR_LOGICALSW "L01""L02""L03""L04""L05""L06""L07""L08""L09""L10""L11""L12""L13""L14""L15""L16""L17""L18""L19""L20""L21""L22""L23""L24""L25""L26""L27""L28""L29""L30""L31""L32" + #define TR_LOGICALSW "L01""L02""L03""L04""L05""L06""L07""L08""L09""L10""L11""L12""L13""L14""L15""L16""L17""L18""L19""L20""L21""L22""L23""L24""L25""L26""L27""L28""L29""L30""L31""L32" #else - #define TR_LOGICALSW "L01""L02""L03""L04""L05""L06""L07""L08""L09""L10""L11""L12" + #define TR_LOGICALSW "L01""L02""L03""L04""L05""L06""L07""L08""L09""L10""L11""L12" #endif #if defined(PCBHORUS) - #define TR_TRIMS_SWITCHES "\313Dg""\313Dd""\313Pb""\313Ph""\313Gb""\313Gh""\313Ag""\313Ad""\3135d""\3135u""\3136d""\3136u" + #define TR_TRIMS_SWITCHES "\313Dg""\313Dd""\313Pb""\313Ph""\313Gb""\313Gh""\313Ag""\313Ad""\3135d""\3135u""\3136d""\3136u" #else - #define TR_TRIMS_SWITCHES TR("tDg""tDd""tPb""tPh""tGb""tGh""tAg""tAd", "\313Dg""\313Dd""\313Pb""\313Ph""\313Gb""\313Gh""\313Ag""\313Ad") + #define TR_TRIMS_SWITCHES TR("tDg""tDd""tPb""tPh""tGb""tGh""tAg""tAd", "\313Dg""\313Dd""\313Pb""\313Ph""\313Gb""\313Gh""\313Ag""\313Ad") #endif #if defined(PCBSKY9X) - #define TR_ROTARY_ENCODERS "REa\0" - #define TR_ROTENC_SWITCHES "REa" + #define TR_ROTARY_ENCODERS "REa\0" + #define TR_ROTENC_SWITCHES "REa" #elif defined(PCBGRUVIN9X) || defined(PCBMEGA2560) - #define TR_ROTARY_ENCODERS "REa\0""REb\0" - #define TR_ROTENC_SWITCHES "REa""REb" + #define TR_ROTARY_ENCODERS "REa\0""REb\0" + #define TR_ROTENC_SWITCHES "REa""REb" #else #define TR_ROTARY_ENCODERS #define TR_ROTENC_SWITCHES #endif #if !defined(PCBTARANIS) - #define TR_2POS_SWITCHES "THR""RUD""ELE""AIL""GEA""TRN" + #define TR_2POS_SWITCHES "THR""RUD""ELE""AIL""GEA""TRN" #endif -#define TR_ON_ONE_SWITCHES "ON\0""Un" +#define TR_ON_ONE_SWITCHES "ON\0""Un" #if defined(PCBFLAMENCO) - #define TR_VSWITCHES "---" TR_PHYS_SWITCHES TR_TRIMS_SWITCHES TR_ROTENC_SWITCHES TR_LOGICALSW "ON\0""One" + #define TR_VSWITCHES "---" TR_PHYS_SWITCHES TR_TRIMS_SWITCHES TR_ROTENC_SWITCHES TR_LOGICALSW "ON\0""One" #elif defined(PCBTARANIS) || defined(PCBHORUS) // only special switches here - #define TR_VSWITCHES "---" TR_TRIMS_SWITCHES TR_ON_ONE_SWITCHES + #define TR_VSWITCHES "---" TR_TRIMS_SWITCHES TR_ON_ONE_SWITCHES #elif defined(PCBSKY9X) - #define TR_VSWITCHES "---" TR_9X_3POS_SWITCHES TR_2POS_SWITCHES TR_TRIMS_SWITCHES TR_ROTENC_SWITCHES TR_ON_ONE_SWITCHES + #define TR_VSWITCHES "---" TR_9X_3POS_SWITCHES TR_2POS_SWITCHES TR_TRIMS_SWITCHES TR_ROTENC_SWITCHES TR_ON_ONE_SWITCHES #else - #define TR_VSWITCHES "---" TR_9X_3POS_SWITCHES TR_2POS_SWITCHES TR_TRIMS_SWITCHES TR_ROTENC_SWITCHES TR_LOGICALSW TR_ON_ONE_SWITCHES + #define TR_VSWITCHES "---" TR_9X_3POS_SWITCHES TR_2POS_SWITCHES TR_TRIMS_SWITCHES TR_ROTENC_SWITCHES TR_LOGICALSW TR_ON_ONE_SWITCHES #endif #if defined(HELI) - #define TR_CYC_VSRCRAW "CYC1""CYC2""CYC3" + #define TR_CYC_VSRCRAW "CYC1""CYC2""CYC3" #else - #define TR_CYC_VSRCRAW "[C1]""[C2]""[C3]" + #define TR_CYC_VSRCRAW "[C1]""[C2]""[C3]" #endif #if defined(CPUARM) - #define TR_RESERVE_VSRCRAW "[--]" - #define TR_EXTRA_VSRCRAW "Batt""H:M\0""GPS\0" TR_RESERVE_VSRCRAW TR_RESERVE_VSRCRAW TR_RESERVE_VSRCRAW TR_RESERVE_VSRCRAW "Chr1""Chr2""Chr3" + #define TR_RESERVE_VSRCRAW "[--]" + #define TR_EXTRA_VSRCRAW "Batt""H:M\0""GPS\0" TR_RESERVE_VSRCRAW TR_RESERVE_VSRCRAW TR_RESERVE_VSRCRAW TR_RESERVE_VSRCRAW "Chr1""Chr2""Chr3" #else #define TR_EXTRA_VSRCRAW - #define TR_VTELEMCHNS "---\0""Batt" TR_TELEM_TIME TR_TELEM_RESERVE TR_TELEM_RESERVE TR_TELEM_RESERVE TR_TELEM_RESERVE TR_TELEM_RESERVE TR_TELEM_TIMERS TR_SWR "Tx\0 " TR_TELEM_RSSI_RX TR_RX_BATT "A1\0 ""A2\0 " TR_A3_A4 "Alt\0""Rpm\0""Carb""T1\0 ""T2\0 ""Vit\0""Dist""AltG""Elem""Velm""Vfas""Cour""Cnsm""Puis""AccX""AccY""AccZ""Cap\0""VitV""VitA""dET\0" TR_TELEM_RESERVE TR_TELEM_RESERVE TR_TELEM_RESERVE TR_TELEM_RESERVE TR_TELEM_RESERVE "A1-\0""A2-\0" TR_A3_A4_MIN "Alt-""Alt+""Rpm+""T1+\0""T2+\0""Vit+""Dst+" TR_ASPD_MAX "Elm-""Els-""Vfs-""Cur+""Pui+" TR_TELEM_RESERVE TR_TELEM_RESERVE TR_TELEM_RESERVE TR_TELEM_RESERVE TR_TELEM_RESERVE "Acc\0""Tmps" + #define TR_VTELEMCHNS "---\0""Batt" TR_TELEM_TIME TR_TELEM_RESERVE TR_TELEM_RESERVE TR_TELEM_RESERVE TR_TELEM_RESERVE TR_TELEM_RESERVE TR_TELEM_TIMERS TR_SWR "Tx\0 " TR_TELEM_RSSI_RX TR_RX_BATT "A1\0 ""A2\0 " TR_A3_A4 "Alt\0""Rpm\0""Carb""T1\0 ""T2\0 ""Vit\0""Dist""AltG""Elem""Velm""Vfas""Cour""Cnsm""Puis""AccX""AccY""AccZ""Cap\0""VitV""VitA""dET\0" TR_TELEM_RESERVE TR_TELEM_RESERVE TR_TELEM_RESERVE TR_TELEM_RESERVE TR_TELEM_RESERVE "A1-\0""A2-\0" TR_A3_A4_MIN "Alt-""Alt+""Rpm+""T1+\0""T2+\0""Vit+""Dst+" TR_ASPD_MAX "Elm-""Els-""Vfs-""Cur+""Pui+" TR_TELEM_RESERVE TR_TELEM_RESERVE TR_TELEM_RESERVE TR_TELEM_RESERVE TR_TELEM_RESERVE "Acc\0""Tmps" #endif -#define TR_VSRCRAW "---\0" TR_STICKS_VSRCRAW TR_POTS_VSRCRAW TR_ROTARY_ENCODERS "MAX\0" TR_CYC_VSRCRAW TR_TRIMS_VSRCRAW TR_SW_VSRCRAW TR_EXTRA_VSRCRAW +#define TR_VSRCRAW "---\0" TR_STICKS_VSRCRAW TR_POTS_VSRCRAW TR_ROTARY_ENCODERS "MAX\0" TR_CYC_VSRCRAW TR_TRIMS_VSRCRAW TR_SW_VSRCRAW TR_EXTRA_VSRCRAW -#define LEN_VTMRMODES "\003" -#define TR_VTMRMODES "OFF""ON\0""GZs""GZ%""GZt" +#define LEN_VTMRMODES "\003" +#define TR_VTMRMODES "OFF""ON\0""GZs""GZ%""GZt" #define LEN_VTRAINERMODES "\022" #define TR_VTRAINER_MASTER_JACK "Maître/Jack\0 " #define TR_VTRAINER_SLAVE_JACK "Elève/Jack\0 " #define TR_VTRAINER_MASTER_SBUS_MODULE "Maître/SBUS Module" #define TR_VTRAINER_MASTER_CPPM_MODULE "Maître/CPPM Module" -#define TR_VTRAINER_MASTER_BATTERY "Maître/Batterie\0" +#define TR_VTRAINER_MASTER_BATTERY "Maître/Batterie\0 " +#define TR_VTRAINER_BLUETOOTH TR("Maître/BT\0 ""Elève/BT\0", "Maître/Bluetooth\0 ""Elève/Bluetooth\0 ") -#define LEN_VFAILSAFE "\011" -#define TR_VFAILSAFE TR("Pas déf.\0""Maintien\0""Prédéf.\0 ""Pas d'imp""Récepteur", "Pas déf.\0""Maintien\0""Prédéfini""Pas d'imp""Récepteur") +#define LEN_VFAILSAFE "\011" +#define TR_VFAILSAFE TR("Pas déf.\0""Maintien\0""Prédéf.\0 ""Pas d'imp""Récepteur", "Pas déf.\0""Maintien\0""Prédéfini""Pas d'imp""Récepteur") #if defined(TELEMETRY_MAVLINK) - #define LEN_MAVLINK_BAUDS "\006" - #define TR_MAVLINK_BAUDS "4800 ""9600 ""14400 ""19200 ""38400 ""57600 ""58798 ""76800" - #define LEN_MAVLINK_AC_MODES "\011" - #define TR_MAVLINK_AC_MODES "Stabilize""Acro ""Alt Hold ""Auto ""Guided ""Loiter ""RTL ""Circle ""Pos Hold ""Land ""OF Loiter""Toy A ""Toy M ""INVALID " - #define LEN_MAVLINK_AP_MODES "\015" - #define TR_MAVLINK_AP_MODES "Manual ""Circle ""Stabilize ""Training ""Fly by Wire A""Fly by Wire A""Auto ""RTL ""Loiter ""Guided ""Initialising ""INVALID " + #define LEN_MAVLINK_BAUDS "\006" + #define TR_MAVLINK_BAUDS "4800 ""9600 ""14400 ""19200 ""38400 ""57600 ""58798 ""76800" + #define LEN_MAVLINK_AC_MODES "\011" + #define TR_MAVLINK_AC_MODES "Stabilize""Acro ""Alt Hold ""Auto ""Guided ""Loiter ""RTL ""Circle ""Pos Hold ""Land ""OF Loiter""Toy A ""Toy M ""INVALID " + #define LEN_MAVLINK_AP_MODES "\015" + #define TR_MAVLINK_AP_MODES "Manual ""Circle ""Stabilize ""Training ""Fly by Wire A""Fly by Wire A""Auto ""RTL ""Loiter ""Guided ""Initialising ""INVALID " #endif -#define LEN_VSENSORTYPES "\012" -#define TR_VSENSORTYPES "Perso\0 ""Calculé\0 " +#define LEN_VSENSORTYPES "\012" +#define TR_VSENSORTYPES "Perso\0 ""Calculé\0 " -#define LEN_VFORMULAS "\010" -#define TR_VFORMULAS "Addition""Moyenne\0""Min\0 ""Max\0 ""Multipl.""Totalise""Elément\0""Consomm.""Distance" +#define LEN_VFORMULAS "\010" +#define TR_VFORMULAS "Addition""Moyenne\0""Min\0 ""Max\0 ""Multipl.""Totalise""Elément\0""Consomm.""Distance" -#define LEN_VPREC "\004" -#define TR_VPREC "0.--""0.0 ""0.00" +#define LEN_VPREC "\004" +#define TR_VPREC "0.--""0.0 ""0.00" -#define LEN_VCELLINDEX "\007" -#define TR_VCELLINDEX "Mini.\0 ""1\0 ""2\0 ""3\0 ""4\0 ""5\0 ""6\0 ""Maxi.\0 ""Diff.\0 " +#define LEN_VCELLINDEX "\007" +#define TR_VCELLINDEX "Mini.\0 ""1\0 ""2\0 ""3\0 ""4\0 ""5\0 ""6\0 ""Maxi.\0 ""Diff.\0 " -#define LEN_VANTENNATYPES "\007" -#define TR_VANTENNATYPES "Interne""Ext+Int\0" +#define LEN_VANTENNATYPES "\007" +#define TR_VANTENNATYPES "Interne""Ext+Int\0" // ZERO TERMINATED STRINGS #if defined(COLORLCD) - #define INDENT " " - #define LEN_INDENT 3 - #define INDENT_WIDTH 12 - #define BREAKSPACE "\036" -#else - #define INDENT "\001" - #define LEN_INDENT 1 - #define INDENT_WIDTH (FW/2) - #define BREAKSPACE " " + #define INDENT " " + #define LEN_INDENT 3 + #define INDENT_WIDTH 12 + #define BREAKSPACE "\036" +#else + #define INDENT "\001" + #define LEN_INDENT 1 + #define INDENT_WIDTH (FW/2) + #define BREAKSPACE " " #endif #if defined(PCBTARANIS) || defined(PCBFLAMENCO) || defined(PCBHORUS) - #define TR_ENTER "[ENTER]" + #define TR_ENTER "[ENTER]" #else - #define TR_ENTER "[MENU]" + #define TR_ENTER "[MENU]" #endif #if defined(PCBHORUS) - #define TR_EXIT "[RTN]" + #define TR_EXIT "[RTN]" #else - #define TR_EXIT "[EXIT]" + #define TR_EXIT "[EXIT]" #endif #if defined(PCBTARANIS) - #define TR_POPUPS TR_EXIT "\010" "\010" "\010" "\010" TR_ENTER + #define TR_POPUPS TR(TR_EXIT "\010" TR_ENTER, TR_EXIT "\010" "\010" "\010" "\010" TR_ENTER) #else - #define TR_POPUPS TR_ENTER "\010" TR_EXIT - #define OFS_EXIT sizeof(TR_ENTER) + #define TR_POPUPS TR_ENTER "\010" TR_EXIT + #define OFS_EXIT sizeof(TR_ENTER) #endif -#define TR_MENUWHENDONE CENTER "\006" TR_ENTER " QUAND PRET" -#define TR_FREE "disp" -#define TR_DELETEMODEL "SUPPRIMER" BREAKSPACE "MODELE" -#define TR_COPYINGMODEL "Copie..." -#define TR_MOVINGMODEL "Déplacement..." -#define TR_LOADINGMODEL "Chargement..." -#define TR_NAME "Nom" -#define TR_MODELNAME TR("Nom modèle", "Nom du modèle") -#define TR_PHASENAME "Nom phase" -#define TR_MIXNAME TR("Nom ligne", "Nom du mixeur") -#define TR_INPUTNAME TR("Entrée", "Nom entrée") -#define TR_EXPONAME TR("Nom", "Nom ligne") -#define TR_BITMAP "Image du modèle" -#define TR_TIMER "Chrono " -#define TR_ELIMITS TR("Limites ét.", "Limites étendues") -#define TR_ETRIMS TR("Trims ét.", "Trims étendus") -#define TR_TRIMINC TR("Pas Trim", "Pas des trims") -#define TR_DISPLAY_TRIMS TR("Aff. trims", "Affichage trims") -#define TR_TTRACE TR("Source gaz", INDENT "Source") -#define TR_TTRIM TR("Trim gaz", INDENT "Trim ralenti uniq.") -#define TR_BEEPCTR TR("Bips centr", "Bips centrage") -#define TR_USE_GLOBAL_FUNCS TR("Fonc. glob.", "Fonctions globales") +#define TR_MENUWHENDONE CENTER "\006" TR_ENTER " QUAND PRET" +#define TR_FREE "disp" +#define TR_DELETEMODEL "SUPPRIMER" BREAKSPACE "MODELE" +#define TR_COPYINGMODEL "Copie..." +#define TR_MOVINGMODEL "Déplacement..." +#define TR_LOADINGMODEL "Chargement..." +#define TR_NAME "Nom" +#define TR_MODELNAME TR("Nom modèle", "Nom du modèle") +#define TR_PHASENAME "Nom phase" +#define TR_MIXNAME TR("Nom ligne", "Nom du mixeur") +#define TR_INPUTNAME TR("Entrée", "Nom entrée") +#define TR_EXPONAME TR("Nom", "Nom ligne") +#define TR_BITMAP "Image du modèle" +#define TR_TIMER "Chrono " +#define TR_ELIMITS TR("Limites ét.", "Limites étendues") +#define TR_ETRIMS TR("Trims ét.", "Trims étendus") +#define TR_TRIMINC TR("Pas Trim", "Pas des trims") +#define TR_DISPLAY_TRIMS TR("Aff. trims", "Affichage trims") +#define TR_TTRACE TR("Source gaz", INDENT "Source") +#define TR_TTRIM TR("Trim gaz", INDENT "Trim ralenti uniq.") +#define TR_BEEPCTR TR("Bips centr", "Bips centrage") +#define TR_USE_GLOBAL_FUNCS TR("Fonc. glob.", "Fonctions globales") #if defined(PCBSKY9X) && defined(REVX) - #define TR_OUTPUT_TYPE INDENT "Sortie" + #define TR_OUTPUT_TYPE INDENT "Sortie" #endif -#define TR_PROTO TR(INDENT "Proto.", INDENT "Protocole") +#define TR_PROTO TR(INDENT "Proto.", INDENT "Protocole") #if defined(CPUARM) - #define TR_PPMFRAME INDENT "Trame PPM" -#else - #define TR_PPMFRAME "Trame PPM" -#endif -#define TR_MS "ms" -#define TR_SWITCH TR("Inter", "Interrupteur") -#define TR_TRIMS "Trims" -#define TR_FADEIN "Fondu ON" -#define TR_FADEOUT "Fondu OFF" -#define TR_DEFAULT "(défaut)" -#define TR_CHECKTRIMS "\006Vérif\012Trims" -#define OFS_CHECKTRIMS (9*FW) -#define TR_SWASHTYPE TR("Type de Plat.", "Type de plateau") -#define TR_COLLECTIVE TR("Collectif", "Source collectif") -#define TR_AILERON "Source cyc. lat." -#define TR_ELEVATOR "Source cyc. lon." -#define TR_SWASHRING TR("Limite Cycl.", "Limite du cyclique") -#define TR_ELEDIRECTION TR("Inv. longitud.", "Inversion longitudinal") -#define TR_AILDIRECTION TR("Inv. latéral", "Inversion latéral") -#define TR_COLDIRECTION TR("Inv. collectif", "Inversion collectif") -#define TR_MODE INDENT "Mode" -#define TR_SUBTYPE INDENT "Sous-type" -#define TR_NOFREEEXPO "Max expos atteint!" -#define TR_NOFREEMIXER "Max mixages atteint!" -#define TR_SOURCE INDENT "Source" -#define TR_WEIGHT "Ratio" -#define TR_EXPO TR("Expo", "Exponentiel") -#define TR_SIDE "Coté" -#define TR_DIFFERENTIAL "Différentiel" -#define TR_OFFSET INDENT "Décalage" -#define TR_TRIM "Trim" -#define TR_DREX "DRex" -#define DREX_CHBOX_OFFSET 30 -#define TR_CURVE "Courbe" -#define TR_FLMODE TR("Phase", "Phases") -#define TR_MIXWARNING "Alerte" -#define TR_OFF "OFF" -#define TR_MULTPX "Opération" -#define TR_DELAYDOWN "Retard bas" -#define TR_DELAYUP "Retard haut" -#define TR_SLOWDOWN "Ralenti bas" -#define TR_SLOWUP "Ralenti haut" -#define TR_MIXER "MIXEUR" -#define TR_CV "CB" -#define TR_GV TR("G", "VG") -#define TR_ACHANNEL "A" -#define TR_RANGE INDENT "Plage" -#define TR_CENTER INDENT "Centre" -#define TR_BAR "Barre" -#define TR_ALARM INDENT "Alarme" -#define TR_USRDATA "Données" -#define TR_BLADES INDENT "Pales" -#define TR_SCREEN "Ecran " -#define TR_SOUND_LABEL "Son" -#define TR_LENGTH INDENT "Durée" -#define TR_BEEP_LENGTH INDENT "Durée bips" -#define TR_SPKRPITCH INDENT "Tonalité" -#define TR_HAPTIC_LABEL "Vibreur" -#define TR_HAPTICSTRENGTH INDENT "Force" -#define TR_CONTRAST "Contraste" -#define TR_ALARMS_LABEL "Alarmes" -#define TR_BATTERY_RANGE "Plage batterie" -#define TR_BATTERYWARNING TR(INDENT "Batterie", INDENT "Batterie faible") -#define TR_INACTIVITYALARM INDENT "Inactivité" -#define TR_MEMORYWARNING INDENT "Mémoire pleine" -#define TR_ALARMWARNING TR(INDENT "Silence", INDENT "Sons désactivés") -#define TR_RENAVIG "Navig EncRot" -#define TR_THROTTLE_LABEL "Gaz" -#define TR_THROTTLEREVERSE TR("Inv. gaz", INDENT "Inversion gaz") -#define TR_TIMER_NAME INDENT "Nom" -#define TR_MINUTEBEEP TR(INDENT "Bip min.", INDENT "Annonces minutes") -#define TR_BEEPCOUNTDOWN TR(INDENT "Bip fin", INDENT "Compte à rebours") -#define TR_PERSISTENT TR(INDENT "Persist.", INDENT "Persistant") -#define TR_BACKLIGHT_LABEL "Rétroéclairage" -#define TR_BLDELAY INDENT "Durée" -#define TR_BLONBRIGHTNESS INDENT "Luminosité ON" -#define TR_BLOFFBRIGHTNESS INDENT "Luminosité OFF" -#define TR_BLCOLOR INDENT "Couleur" -#define TR_SPLASHSCREEN "Logo d'accueil" -#define TR_THROTTLEWARNING TR(IF_CPUARM(INDENT) "Alerte gaz", INDENT "Alerte gaz") -#define TR_SWITCHWARNING TR(IF_CPUARM(INDENT) "Alerte int", INDENT "Pos. interrupteurs") -#define TR_POTWARNINGSTATE TR(IF_CPUARM(INDENT) "Pot&Slid.", INDENT "Pots & sliders") -#define TR_SLIDERWARNING TR(IF_CPUARM(INDENT) "Slid. pos.", INDENT "Slider positions") -#define TR_POTWARNING TR(IF_CPUARM(INDENT) "Alerte pot", INDENT "Pos. potentios") -#define TR_TIMEZONE "Fuseau horaire" -#define TR_ADJUST_RTC TR("Ajust. RTC", INDENT "Ajust. heure auto") -#define TR_GPS "GPS" -#define TR_RXCHANNELORD TR("Ordre voies RX","Ordre des voies préféré") -#define TR_STICKS "Manches" -#define TR_POTS "Potentiomètres" -#define TR_SWITCHES "Inters" -#define TR_SWITCHES_DELAY "Délai inters son" -#define TR_SLAVE "Elève" -#define TR_MODESRC "Mode\006% Source" -#define TR_MULTIPLIER "Multiplieur" -#define TR_CAL "Cal" -#define TR_VTRIM "Trim- +" -#define TR_BG "BG:" + #define TR_PPMFRAME INDENT "Trame PPM" +#define TR_REFRESHRATE TR(INDENT "Refresh", INDENT "Refresh rate") +#define STR_WARN_BATTVOLTAGE TR(INDENT "Output is VBAT: ", INDENT "Warning: output level is VBAT: ") +#else + #define TR_PPMFRAME "Trame PPM" +#endif +#define TR_MS "ms" +#define TR_SWITCH TR("Inter", "Interrupteur") +#define TR_TRIMS "Trims" +#define TR_FADEIN "Fondu ON" +#define TR_FADEOUT "Fondu OFF" +#define TR_DEFAULT "(défaut)" +#define TR_CHECKTRIMS "\006Vérif\012Trims" +#define OFS_CHECKTRIMS (9*FW) +#define TR_SWASHTYPE TR("Type de Plat.", "Type de plateau") +#define TR_COLLECTIVE TR("Collectif", "Source collectif") +#define TR_AILERON "Source cyc. lat." +#define TR_ELEVATOR "Source cyc. lon." +#define TR_SWASHRING TR("Limite Cycl.", "Limite du cyclique") +#define TR_ELEDIRECTION TR("Inv. longitud.", "Inversion longitudinal") +#define TR_AILDIRECTION TR("Inv. latéral", "Inversion latéral") +#define TR_COLDIRECTION TR("Inv. collectif", "Inversion collectif") +#define TR_MODE INDENT "Mode" +#define TR_SUBTYPE INDENT "Sous-type" +#define TR_NOFREEEXPO "Max expos atteint!" +#define TR_NOFREEMIXER "Max mixages atteint!" +#define TR_SOURCE INDENT "Source" +#define TR_WEIGHT "Ratio" +#define TR_EXPO TR("Expo", "Exponentiel") +#define TR_SIDE "Coté" +#define TR_DIFFERENTIAL "Différentiel" +#define TR_OFFSET INDENT "Décalage" +#define TR_TRIM "Trim" +#define TR_DREX "DRex" +#define DREX_CHBOX_OFFSET 30 +#define TR_CURVE "Courbe" +#define TR_FLMODE TR("Phase", "Phases") +#define TR_MIXWARNING "Alerte" +#define TR_OFF "OFF" +#define TR_MULTPX "Opération" +#define TR_DELAYDOWN "Retard bas" +#define TR_DELAYUP "Retard haut" +#define TR_SLOWDOWN "Ralenti bas" +#define TR_SLOWUP "Ralenti haut" +#define TR_MIXER "MIXEUR" +#define TR_CV "CB" +#define TR_GV TR("G", "VG") +#define TR_ACHANNEL "A" +#define TR_RANGE INDENT "Plage" +#define TR_CENTER INDENT "Centre" +#define TR_BAR "Barre" +#define TR_ALARM INDENT "Alarme" +#define TR_USRDATA "Données" +#define TR_BLADES INDENT "Pales" +#define TR_SCREEN "Ecran " +#define TR_SOUND_LABEL "Son" +#define TR_LENGTH INDENT "Durée" +#define TR_BEEP_LENGTH INDENT "Durée bips" +#define TR_SPKRPITCH INDENT "Tonalité" +#define TR_HAPTIC_LABEL "Vibreur" +#define TR_HAPTICSTRENGTH INDENT "Force" +#define TR_CONTRAST "Contraste" +#define TR_ALARMS_LABEL "Alarmes" +#define TR_BATTERY_RANGE "Plage batterie" +#define TR_BATTERYWARNING TR(INDENT "Batterie", INDENT "Batterie faible") +#define TR_INACTIVITYALARM INDENT "Inactivité" +#define TR_MEMORYWARNING INDENT "Mémoire pleine" +#define TR_ALARMWARNING TR(INDENT "Silence", INDENT "Sons désactivés") +#define TR_RSSISHUTDOWNALARM TR(INDENT "Rssi Shutdown", INDENT "Check Rssi on Shutdown") +#define TR_MODEL_STILL_POWERED "Modèle encore allumé" +#define TR_PRESS_ENTER_TO_CONFIRM "Presser [Enter] pour confirmer" +#define TR_RENAVIG "Navig EncRot" +#define TR_THROTTLE_LABEL "Gaz" +#define TR_THROTTLEREVERSE TR("Inv. gaz", INDENT "Inversion gaz") +#define TR_TIMER_NAME INDENT "Nom" +#define TR_MINUTEBEEP TR(INDENT "Bip min.", INDENT "Annonces minutes") +#define TR_BEEPCOUNTDOWN TR(INDENT "Bip fin", INDENT "Compte à rebours") +#define TR_PERSISTENT TR(INDENT "Persist.", INDENT "Persistant") +#define TR_BACKLIGHT_LABEL "Rétroéclairage" +#define TR_BLDELAY INDENT "Durée" +#define TR_BLONBRIGHTNESS INDENT "Luminosité ON" +#define TR_BLOFFBRIGHTNESS INDENT "Luminosité OFF" +#define TR_BLCOLOR INDENT "Couleur" +#define TR_SPLASHSCREEN "Logo d'accueil" +#define TR_THROTTLEWARNING TR(IF_CPUARM(INDENT) "Alerte gaz", INDENT "Alerte gaz") +#define TR_SWITCHWARNING TR(IF_CPUARM(INDENT) "Alerte int", INDENT "Pos. interrupteurs") +#define TR_POTWARNINGSTATE TR(IF_CPUARM(INDENT) "Pot&Slid.", INDENT "Pots & sliders") +#define TR_SLIDERWARNING TR(IF_CPUARM(INDENT) "Slid. pos.", INDENT "Slider positions") +#define TR_POTWARNING TR(IF_CPUARM(INDENT) "Alerte pot", INDENT "Pos. potentios") +#define TR_TIMEZONE "Fuseau horaire" +#define TR_ADJUST_RTC TR("Ajust. RTC", INDENT "Ajust. heure auto") +#define TR_GPS "GPS" +#define TR_RXCHANNELORD TR("Ordre voies RX","Ordre des voies préféré") +#define TR_STICKS "Manches" +#define TR_POTS "Potentiomètres" +#define TR_SWITCHES "Inters" +#define TR_SWITCHES_DELAY "Délai inters son" +#define TR_SLAVE "Elève" +#define TR_MODESRC "Mode\006% Source" +#define TR_MULTIPLIER "Multiplieur" +#define TR_CAL "Cal" +#define TR_VTRIM "Trim- +" +#define TR_BG "BG:" #if defined(PCBHORUS) - #define TR_MENUTOSTART "Presser [Enter] pour commencer" - #define TR_SETMIDPOINT "Centrer manches/pots/sliders puis [Enter]" - #define TR_MOVESTICKSPOTS "Bouger manches/pots/sliders puis [Enter]" + #define TR_MENUTOSTART "Presser [Enter] pour commencer" + #define TR_SETMIDPOINT "Centrer manches/pots/sliders puis [Enter]" + #define TR_MOVESTICKSPOTS "Bouger manches/pots/sliders puis [Enter]" #elif defined(COLORLCD) - #define TR_MENUTOSTART TR_ENTER " POUR DEBUT" - #define TR_SETMIDPOINT "REGLER NEUTRES" - #define TR_MOVESTICKSPOTS "BOUGER STICKS/POTS" -#else - #define TR_MENUTOSTART CENTER"\006" TR_ENTER " POUR DEBUT" - #define TR_SETMIDPOINT CENTER"\010REGLER NEUTRES" - #define TR_MOVESTICKSPOTS CENTER"\004BOUGER STICKS/POTS" -#endif -#define TR_RXBATT "Batt.RX" -#define TR_TXnRX "Tx:\0Rx:" -#define OFS_RX 4 -#define TR_ACCEL "Acc:" -#define TR_NODATA CENTER "NO DATA" -#define TR_TOTTM1TM2THRTHP "\037\146SES\036TM1\037\146TM2\036GAZ\037\146GZ%" -#define TR_TMR1LATMAXUS "Tmr1Lat max\037\124us" -#define STR_US (STR_TMR1LATMAXUS+13) -#define TR_TMR1LATMINUS "Tmr1Lat min\037\124us" -#define TR_TMR1JITTERUS "Tmr1 Jitter\037\124us" + #define TR_MENUTOSTART TR_ENTER " POUR DEBUT" + #define TR_SETMIDPOINT "REGLER NEUTRES" + #define TR_MOVESTICKSPOTS "BOUGER STICKS/POTS" +#else + #define TR_MENUTOSTART CENTER"\006" TR_ENTER " POUR DEBUT" + #define TR_SETMIDPOINT CENTER"\010REGLER NEUTRES" + #define TR_MOVESTICKSPOTS CENTER"\004BOUGER STICKS/POTS" +#endif +#define TR_RXBATT "Batt.RX" +#define TR_TXnRX "Tx:\0Rx:" +#define OFS_RX 4 +#define TR_ACCEL "Acc:" +#define TR_NODATA CENTER "NO DATA" +#define TR_TOTTM1TM2THRTHP "\037\146SES\036TM1\037\146TM2\036GAZ\037\146GZ%" +#define TR_TMR1LATMAXUS "Tmr1Lat max\037\124us" +#define STR_US (STR_TMR1LATMAXUS+13) +#define TR_TMR1LATMINUS "Tmr1Lat min\037\124us" +#define TR_TMR1JITTERUS "Tmr1 Jitter\037\124us" #if defined(CPUARM) - #define TR_TMIXMAXMS "Tmix max" - #define TR_FREESTACKMINB "Free Stack" + #define TR_TMIXMAXMS "Tmix max" + #define TR_FREESTACKMINB "Free Stack" #else - #define TR_TMIXMAXMS "Tmix max\037\124ms" - #define TR_FREESTACKMINB "Free Stack\037\124b" + #define TR_TMIXMAXMS "Tmix max\037\124ms" + #define TR_FREESTACKMINB "Free Stack\037\124b" #endif -#define TR_MENUTORESET CENTER TR_ENTER" pour reset" -#define TR_PPM_TRAINER "TR" -#define TR_CH "CH" -#define TR_MODEL "MODELE" -#define TR_FP "PV" -#define TR_MIX "MIX" -#define TR_EEPROMLOWMEM "EEPROM pleine!" -#define TR_ALERT "\014ALERTE" -#define TR_PRESSANYKEYTOSKIP "Touche pour ignorer" -#define TR_THROTTLENOTIDLE "Gaz pas à zéro" -#define TR_ALARMSDISABLED "Alarmes Désactivées" -#define TR_PRESSANYKEY TR("Touche pour continuer", "Touche pour continuer") -#define TR_BADEEPROMDATA "EEPROM corrompue" -#define TR_BAD_RADIO_DATA "Réglages radio corrompus" -#define TR_EEPROMFORMATTING "Formatage EEPROM" -#define TR_STORAGE_FORMAT "Préparation stockage" -#define TR_EEPROMOVERFLOW "Dépassement EEPROM" -#define TR_MENURADIOSETUP "CONFIG RADIO" -#define TR_MENUDATEANDTIME "DATE ET HEURE" -#define TR_MENUTRAINER "ECOLAGE" -#define TR_MENUSPECIALFUNCS "FONCTIONS GLOBALES" -#define TR_MENUVERSION "VERSION" -#define TR_MENU_RADIO_SWITCHES TR("INTERS", "TEST INTERRUPTEURS") -#define TR_MENU_RADIO_ANALOGS TR("ANAS", "ENTREES ANALOGIQUES") -#define TR_MENUCALIBRATION "CALIBRATION" -#define TR_TRIMS2OFFSETS "\005Trims => Subtrims" -#define TR_MENUMODELSEL "MODELES" -#define TR_MENUSETUP TR("CONF. MODELE", "CONFIGURATION") -#define TR_MENUFLIGHTMODE "PHASE DE VOL" -#define TR_MENUFLIGHTMODES "PHASES DE VOL" -#define TR_MENUHELISETUP TR("CONF.HELI", "CONFIGURATION HELICO") +#define TR_MENUTORESET CENTER TR_ENTER" pour reset" +#define TR_PPM_TRAINER "TR" +#define TR_CH "CH" +#define TR_MODEL "MODELE" +#define TR_FP "PV" +#define TR_MIX "MIX" +#define TR_EEPROMLOWMEM "EEPROM pleine!" +#define TR_ALERT "\014ALERTE" +#define TR_PRESSANYKEYTOSKIP "Touche pour ignorer" +#define TR_THROTTLENOTIDLE "Gaz pas à zéro" +#define TR_ALARMSDISABLED "Alarmes Désactivées" +#define TR_PRESSANYKEY TR("Touche pour continuer", "Touche pour continuer") +#define TR_BADEEPROMDATA "EEPROM corrompue" +#define TR_BAD_RADIO_DATA "Réglages radio corrompus" +#define TR_EEPROMFORMATTING "Formatage EEPROM" +#define TR_STORAGE_FORMAT "Préparation stockage" +#define TR_EEPROMOVERFLOW "Dépassement EEPROM" +#define TR_MENURADIOSETUP "CONFIG RADIO" +#define TR_MENUDATEANDTIME "DATE ET HEURE" +#define TR_MENUTRAINER "ECOLAGE" +#define TR_MENUSPECIALFUNCS "FONCTIONS GLOBALES" +#define TR_MENUVERSION "VERSION" +#define TR_MENU_RADIO_SWITCHES TR("INTERS", "TEST INTERRUPTEURS") +#define TR_MENU_RADIO_ANALOGS TR("ANAS", "ENTREES ANALOGIQUES") +#define TR_MENUCALIBRATION "CALIBRATION" +#define TR_TRIMS2OFFSETS "\005Trims => Subtrims" +#define TR_MENUMODELSEL "MODELES" +#define TR_MENUSETUP TR("CONF. MODELE", "CONFIGURATION") +#define TR_MENUFLIGHTMODE "PHASE DE VOL" +#define TR_MENUFLIGHTMODES "PHASES DE VOL" +#define TR_MENUHELISETUP TR("CONF.HELI", "CONFIGURATION HELICO") #if defined(CPUARM) - #define TR_MENUINPUTS "ENTREES" - #define TR_MENULIMITS "SORTIES" + #define TR_MENUINPUTS "ENTREES" + #define TR_MENULIMITS "SORTIES" #else - #define TR_MENUINPUTS "DR/EXPO" - #define TR_MENULIMITS "LIMITES" + #define TR_MENUINPUTS "DR/EXPO" + #define TR_MENULIMITS "LIMITES" #endif -#define TR_MENUCURVES "COURBES" -#define TR_MENUCURVE "COURBE" -#define TR_MENULOGICALSWITCH "INTER LOG." -#define TR_MENULOGICALSWITCHES TR("INTERS LOG.", "INTERS LOGIQUES") -#define TR_MENUCUSTOMFUNC TR("FONCTIONS SPEC.", "FONCTIONS SPECIALES") -#define TR_MENUCUSTOMSCRIPTS "SCRIPTS PERSOS" -#define TR_MENUTELEMETRY "TELEMESURE" -#define TR_MENUTEMPLATES "GABARITS" -#define TR_MENUSTAT TR("STATS", "STATISTIQUES") -#define TR_MENUDEBUG "DEBUG" -#define TR_MONITOR_CHANNELS1 "VOIES 1-8" -#define TR_MONITOR_CHANNELS2 "VOIES 9-16" -#define TR_MONITOR_CHANNELS3 "VOIES 17-24" -#define TR_MONITOR_CHANNELS4 "VOIES 25-32" -#define TR_MONITOR_SWITCHES "INTERS LOGIQUES" -#define TR_MONITOR_OUTPUT_DESC "Sorties" -#define TR_MONITOR_MIXER_DESC "Mixeurs" +#define TR_MENUCURVES "COURBES" +#define TR_MENUCURVE "COURBE" +#define TR_MENULOGICALSWITCH "INTER LOG." +#define TR_MENULOGICALSWITCHES TR("INTERS LOG.", "INTERS LOGIQUES") +#define TR_MENUCUSTOMFUNC TR("FONCTIONS SPEC.", "FONCTIONS SPECIALES") +#define TR_MENUCUSTOMSCRIPTS "SCRIPTS PERSOS" +#define TR_MENUTELEMETRY "TELEMESURE" +#define TR_MENUTEMPLATES "GABARITS" +#define TR_MENUSTAT TR("STATS", "STATISTIQUES") +#define TR_MENUDEBUG "DEBUG" +#define TR_MONITOR_CHANNELS1 "VOIES 1-8" +#define TR_MONITOR_CHANNELS2 "VOIES 9-16" +#define TR_MONITOR_CHANNELS3 "VOIES 17-24" +#define TR_MONITOR_CHANNELS4 "VOIES 25-32" +#define TR_MONITOR_SWITCHES "INTERS LOGIQUES" +#define TR_MONITOR_OUTPUT_DESC "Sorties" +#define TR_MONITOR_MIXER_DESC "Mixeurs" #if defined(CPUARM) - #define TR_RECEIVER_NUM TR(INDENT "NumRx", INDENT "No. récepteur") - #define TR_RECEIVER INDENT "Récepteur" + #define TR_RECEIVER_NUM TR(INDENT "NumRx", INDENT "No. récepteur") + #define TR_RECEIVER INDENT "Récepteur" #else - #define TR_RECEIVER_NUM "Récepteur" - #define TR_RECEIVER "Récepteur" + #define TR_RECEIVER_NUM "Récepteur" + #define TR_RECEIVER "Récepteur" #endif -#define TR_MULTI_RFTUNE TR(INDENT "Ajust.fréq", INDENT "Ajustement fréq.") +#define TR_MULTI_RFTUNE TR(INDENT "Ajust.fréq", INDENT "Ajustement fréq.") #define TR_MULTI_TELEMETRY "Telemetry" -#define TR_MULTI_VIDFREQ TR(INDENT "Fréq. vidéo", INDENT "Fréquence vidéo") -#define TR_MULTI_RFPOWER TR(INDENT "Puiss. RF", INDENT "Puissance RF") -#define TR_MULTI_OPTION TR(INDENT "Option", INDENT "Option perso") -#define TR_MULTI_AUTOBIND TR(INDENT "Bind auto", INDENT "Bind automatique") -#define TR_MULTI_DSM_AUTODTECT TR(INDENT "Autodét.", INDENT "Autodétection") -#define TR_MULTI_LOWPOWER TR(INDENT "Basse puis.", INDENT "Mode basse puiss.") -#define TR_DISABLE_INTERNAL TR("Désact intRF", "Désact. RF interne") -#define TR_MODULE_NO_SERIAL_MODE TR("Mode série?", "Pas en mode série") -#define TR_MODULE_NO_INPUT TR("Pas de sign.", "Aucun signal série") -#define TR_MODULE_NO_TELEMETRY TR3("Pas de télm.", "Télémétrie absente", "Télémétrie absente(act. MULTI_TELEMETRY)") -#define TR_MODULE_BINDING "Bind..." -#define TR_BINDING_MODE1 "Ch1-8 Telem ON" -#define TR_BINDING_MODE2 "Ch1-8 Telem OFF" -#define TR_BINDING_MODE3 "Ch9-16 Telem ON" -#define TR_BINDING_MODE4 "Ch9-16 Telem OFF" -#define TR_PROTOCOL_INVALID TR("Sél. invalide", "Protocole invalide") -#define TR_MODULE_STATUS TR(INDENT "Etat", INDENT "Etat module") -#define TR_MULTI_SERVOFREQ TR(INDENT "Fréq.servo", INDENT "Fréquence servos") -#define TR_SYNCMENU "Sync [MENU]" -#define TR_LIMIT INDENT "Limite" -#define TR_MINRSSI "RSSI Min." -#define TR_LATITUDE "Latitude" -#define TR_LONGITUDE "Longitude" -#define TR_GPSCOORD TR("Coordonnées", "Coordonnées GPS") -#define TR_VARIO TR("Vario", "Variomètre") -#define TR_PITCH_AT_ZERO INDENT "Tonalité au zéro" -#define TR_PITCH_AT_MAX INDENT "Tonalité au max" -#define TR_REPEAT_AT_ZERO TR(INDENT "Interv. au zéro", INDENT "Intervalle au zéro") -#define TR_POWEROFF "\037\120ARRET..." -#define TR_SHUTDOWN "ARRET EN COURS" -#define TR_SAVEMODEL "Sauvegarde modèle..." -#define TR_BATT_CALIB "Calib. batterie" -#define TR_CURRENT_CALIB "Calib. courant" -#define TR_VOLTAGE TR(INDENT "Tension",INDENT "Source tension") -#define TR_CURRENT TR(INDENT "Courant",INDENT "Source courant") -#define TR_SELECT_MODEL "Sélect. modèle" -#define TR_CREATE_CATEGORY "Créer une catégorie" -#define TR_RENAME_CATEGORY "Renommer la catégorie" -#define TR_DELETE_CATEGORY "Supprimer la catégorie" -#define TR_CREATE_MODEL "Créer modèle" -#define TR_DUPLICATE_MODEL "Dupliquer modèle" -#define TR_COPY_MODEL "Copier modèle" -#define TR_MOVE_MODEL "Déplacer modèle" -#define TR_BACKUP_MODEL "Archiver modèle" -#define TR_DELETE_MODEL "Supprimer modèle" -#define TR_RESTORE_MODEL "Restaurer modèle" -#define TR_DELETE_ERROR "Effacement impossible" -#define TR_CAT_NOT_EMPTY "Categorie non vide" -#define TR_SDCARD_ERROR "Erreur carte SD" -#define TR_NO_SDCARD "Carte SD indisponible" -#define TR_SDCARD_FULL "Carte SD pleine" -#define TR_INCOMPATIBLE "Incompatible" -#define TR_WARNING "ALERTE" -#define TR_EEPROMWARN "EEPROM" -#define TR_STORAGE_WARNING "STOCKAGE" -#define TR_EEPROM_CONVERTING "Conversion EEPROM" -#define TR_THROTTLEWARN "GAZ" -#define TR_ALARMSWARN "SON" -#define TR_SWITCHWARN TR("INTERS","CONTROLES") -#define TR_FAILSAFEWARN "FAILSAFE" -#define TR_WRONG_SDCARDVERSION "Version requise: " -#define TR_WRONG_PCBREV "PCB incorrect détecté" -#define TR_EMERGENCY_MODE "MODE SECOURS" -#define TR_PCBREV_ERROR "Erreur PCB" -#define TR_NO_FAILSAFE "Failsafe pas déf." -#define TR_KEYSTUCK "Touche bloquée" -#define TR_INVERT_THR "Inverser gaz?" -#define TR_SPEAKER_VOLUME INDENT "Volume" -#define TR_LCD "Afficheur" -#define TR_BRIGHTNESS INDENT "Luminosité" -#define TR_CPU_TEMP "Temp. CPU\016>" -#define TR_CPU_CURRENT "Courant\022>" -#define TR_CPU_MAH "Consomm." -#define TR_COPROC "CoProc." -#define TR_COPROC_TEMP "Temp. MB \016>" -#define TR_CAPAWARNING INDENT "Capacité Basse" -#define TR_TEMPWARNING INDENT "Surchauffe" -#define TR_FUNC "Fonction" -#define TR_V1 "V1" -#define TR_V2 "V2" -#define TR_DURATION "Durée" -#define TR_DELAY "Délai" -#define TR_SD_CARD "Carte SD" -#define TR_SDHC_CARD "Carte SD-HC" -#define TR_NO_SOUNDS_ON_SD "Aucun son sur SD" -#define TR_NO_MODELS_ON_SD "Aucun modèle SD" -#define TR_NO_BITMAPS_ON_SD "Aucun Bitmap SD" -#define TR_NO_SCRIPTS_ON_SD "Aucun Script SD" -#define TR_SCRIPT_SYNTAX_ERROR "Erreur syntaxe script" -#define TR_SCRIPT_PANIC "Script bloqué" -#define TR_SCRIPT_KILLED "Script interrompu" -#define TR_SCRIPT_ERROR "Erreur inconnue" -#define TR_PLAY_FILE "Lire" -#define TR_DELETE_FILE "Supprimer" -#define TR_COPY_FILE "Copier" -#define TR_RENAME_FILE "Renommer" -#define TR_ASSIGN_BITMAP "Sélectionner image" -#define TR_EXECUTE_FILE "Exécuter" -#define TR_REMOVED " supprimé" -#define TR_SD_INFO "Information" -#define TR_SD_FORMAT "Formater" -#define TR_NA "N/D" -#define TR_HARDWARE "MATERIEL" -#define TR_FORMATTING "Formatage..." -#define TR_TEMP_CALIB "Calib. temp" -#define TR_TIME "Heure" -#define TR_BAUDRATE "Baudrate BT" -#define TR_SD_INFO_TITLE "INFO SD" -#define TR_SD_TYPE "Type:" -#define TR_SD_SPEED "Vitesse:" -#define TR_SD_SECTORS "Secteurs:" -#define TR_SD_SIZE "Taille:" -#define TR_TYPE INDENT "Type" -#define TR_GLOBAL_VARS "Variables Globales" -#define TR_GVARS "V. GLOBALES" -#define TR_GLOBAL_VAR "Variable globale" -#define TR_MENUGLOBALVARS "VARIABLES GLOBALES" -#define TR_OWN "Pers" -#define TR_DATE "Date" -#define TR_MONTHS { "Jan", "Fév", "Mar", "Avr", "Mai", "Jun", "Jul", "Aou", "Sep", "Oct", "Nov", "Dec" } -#define TR_ROTARY_ENCODER "Enc.Rot." -#define TR_CHANNELS_MONITOR "MONITEUR CANAUX" -#define TR_MIXERS_MONITOR "MONITEUR MIXAGES " -#define TR_PATH_TOO_LONG "Chemin trop long" -#define TR_VIEW_TEXT "Voir texte" -#define TR_FLASH_BOOTLOADER "Flasher BootLoader" -#define TR_FLASH_EXTERNAL_DEVICE TR("Flasher module ext.", "Flasher module externe") -#define TR_FLASH_INTERNAL_MODULE TR("Flasher module int.", "Flasher module interne") -#define TR_FIRMWARE_UPDATE_ERROR "Firmware update error" -#define TR_WRITING TR("\14Ecriture...", "\032Ecriture...") -#define TR_CONFIRM_FORMAT "Confirmer Formatage?" -#define TR_INTERNALRF "HF interne" -#define TR_EXTERNALRF "HF externe" -#define TR_FAILSAFE TR(INDENT "Failsafe", INDENT "Type failsafe") -#define TR_FAILSAFESET "REGLAGES FAILSAFE" -#define TR_HOLD "HOLD" -#define TR_NONE "NONE" -#define TR_MENUSENSOR "CAPTEUR" -#define TR_SENSOR "SENSOR" -#define TR_COUNTRYCODE TR("Zone géo.", "Zone géographique") -#define TR_VOICELANG TR("Langue voix", "Langue annonces vocales") -#define TR_UNITSSYSTEM "Unités" -#define TR_EDIT "Editer" -#define TR_INSERT_BEFORE "Insérer avant" -#define TR_INSERT_AFTER "Insérer après" -#define TR_COPY "Copier" -#define TR_MOVE "Déplacer" -#define TR_PASTE "Coller" -#define TR_DELETE "Supprimer" -#define TR_INSERT "Insérer" -#define TR_RESET_FLIGHT TR("Réinit. vol", "Réinitialiser vol") -#define TR_RESET_TIMER1 TR("Réinit. Timer1", "Réinitialiser Timer1") -#define TR_RESET_TIMER2 TR("Réinit. Timer2", "Réinitialiser Timer2") -#define TR_RESET_TIMER3 TR("Réinit. Timer3", "Réinitialiser Timer3") -#define TR_RESET_TELEMETRY TR("Réinit. Télém.", "Réinit. Télémesure") -#define TR_STATISTICS "Statistiques" -#define TR_ABOUT_US "A propos" -#define TR_SETUP_SCREENS "Configuration écrans" -#define TR_MONITOR_SCREENS "Moniteurs" -#define TR_AND_SWITCH "ET suppl." -#define TR_SF "FS" -#define TR_GF "FG" -#define TR_SPEAKER INDENT "Haut-p." -#define TR_BUZZER INDENT "Bipeur" -#define TR_BYTES "bytes" -#define TR_MODULE_BIND BUTTON(TR("Bnd", "Bind")) -#define TR_MODULE_RANGE BUTTON(TR("Prt", "Port.")) -#define TR_RESET_BTN BUTTON("RAZ") -#define TR_SET BUTTON("Déf") -#define TR_TRAINER "Ecolage" -#define TR_ANTENNAPROBLEM CENTER "Antenne radio défectueuse!" -#define TR_MODELIDUSED TR("ID déjà affecté", "No de modèle déjà utilisé") -#define TR_MODULE INDENT "Type de module" -#define TR_TELEMETRY_TYPE TR("Type tél.", "Type télémesure") -#define TR_TELEMETRY_SENSORS "Capteurs" -#define TR_VALUE "Valeur" -#define TR_TOPLCDTIMER "Timer LCD haut" -#define TR_UNIT "Unité" -#define TR_TELEMETRY_NEWSENSOR TR(INDENT"Nouveau capteur...", INDENT "Ajout d'un nouveau capteur...") -#define TR_CHANNELRANGE TR(INDENT "Canaux", INDENT "Plage de canaux") -#define TR_ANTENNASELECTION INDENT "Choix antenne" -#define TR_ANTENNACONFIRM1 "Vraiment changer?" -#define TR_ANTENNACONFIRM2 "Installer l'antenne d'abord!" -#define TR_LOWALARM INDENT "Alarme basse" -#define TR_CRITICALALARM INDENT "Alarme critique" -#define TR_ENABLE_POPUP "Activer popup" -#define TR_DISABLE_POPUP "Désactiver popup" -#define TR_POPUP "Popup" -#define TR_MIN "Min" -#define TR_MAX "Max" -#define TR_CURVE_PRESET "Courbe standard..." -#define TR_PRESET "Pente" -#define TR_MIRROR "Miroir" -#define TR_CLEAR "Effacer" -#define TR_RESET "Réinitialiser" -#define TR_RESET_SUBMENU "Réinitialiser..." -#define TR_COUNT "Nb points" -#define TR_PT "pt" -#define TR_PTS "pts" -#define TR_SMOOTH "Lissage" -#define TR_COPY_STICKS_TO_OFS TR("Cpy stick->subtrim", "Manche vers subtrim") -#define TR_COPY_TRIMS_TO_OFS TR("Cpy trim->subtrim", "Trim vers subtrim") -#define TR_INCDEC "Inc/décrementer" -#define TR_GLOBALVAR "Var. globale" -#define TR_MIXSOURCE "Source mixeur" -#define TR_CONSTANT "Constante" -#define TR_PERSISTENT_MAH TR(INDENT "Enr. mAh", INDENT "Enregistrer mAh") -#define TR_PREFLIGHT "Vérifications avant vol" -#define TR_CHECKLIST TR(INDENT "Notes", INDENT "Afficher notes") -#define TR_FAS_OFFSET TR(INDENT "Corr FAS", INDENT "Correction FAS") -#define TR_UART3MODE "Port série" -#define TR_SCRIPT "Script" -#define TR_INPUTS "Entrées" -#define TR_OUTPUTS "Sorties" -#define TR_EEBACKUP TR("[ENTER Long]:Sauvegarde", "\004[ENTER Long]: Sauvegarder l'EEPROM") -#define TR_FACTORYRESET TR("\001[MENU Long]: RAZ d'usine", "\016[MENU Long]: RAZ d'usine") -#define TR_CONFIRMRESET TR("Effacer TOUT?","Effacer TOUS modèles/réglages?") -#define TR_TO_MANY_LUA_SCRIPTS "Trop de scripts lua!" +#define TR_MULTI_VIDFREQ TR(INDENT "Fréq. vidéo", INDENT "Fréquence vidéo") +#define TR_MULTI_RFPOWER TR(INDENT "Puiss. RF", INDENT "Puissance RF") +#define TR_MULTI_OPTION TR(INDENT "Option", INDENT "Option perso") +#define TR_MULTI_AUTOBIND TR(INDENT "Bind auto", INDENT "Bind automatique") +#define TR_MULTI_DSM_AUTODTECT TR(INDENT "Autodét.", INDENT "Autodétection") +#define TR_MULTI_LOWPOWER TR(INDENT "Basse puis.", INDENT "Mode basse puiss.") +#define TR_MODULE_TELEMETRY TR(INDENT "Télem. mod.", INDENT "Télémétrie module") +#define TR_DISABLE_INTERNAL TR("Désact intRF", "Désact. RF interne") +#define TR_MODULE_NO_SERIAL_MODE TR("Mode série?", "Pas en mode série") +#define TR_MODULE_NO_INPUT TR("Pas de sign.", "Aucun signal série") +#define TR_MODULE_NO_TELEMETRY TR3("Pas de télm.", "Télémétrie absente", "Télémétrie absente(act. MULTI_TELEMETRY)") +#define TR_MODULE_WAITFORBIND "Binder d'abord" +#define TR_MODULE_BINDING "Bind..." +#define TR_BINDING_CH1_8_TELEM_ON "Ch1-8 Télem ON" +#define TR_BINDING_CH1_8_TELEM_OFF "Ch1-8 Télem OFF" +#define TR_BINDING_CH9_16_TELEM_ON "Ch9-16 Télem ON" +#define TR_BINDING_CH9_16_TELEM_OFF "Ch9-16 Télem OFF" +#define TR_BINDING_25MW_CH1_8_TELEM_OFF "25mW Ch1-8 Télem OFF" +#define TR_BINDING_25MW_CH1_8_TELEM_ON "25mW Ch1-8 Télem ON" +#define TR_BINDING_500MW_CH1_8_TELEM_OFF "500mW Ch1-8 Télem OFF" +#define TR_BINDING_500MW_CH9_16_TELEM_OFF "500mW Ch9-16 Télem OFF" +#define TR_BINDING_OPTION "Set at bind" +#define TR_PROTOCOL_INVALID TR("Sél. invalide", "Protocole invalide") +#define TR_MODULE_STATUS TR(INDENT "Etat", INDENT "Etat module") +#define TR_MODULE_SYNC TR(INDENT "Sync", INDENT "Module Sync") +#define TR_MULTI_SERVOFREQ TR(INDENT "Fréq.servo", INDENT "Fréquence servos") +#define TR_SYNCMENU "Sync [MENU]" +#define TR_LIMIT INDENT "Limite" +#define TR_MINRSSI "RSSI Min." +#define TR_LATITUDE "Latitude" +#define TR_LONGITUDE "Longitude" +#define TR_GPSCOORD TR("Coordonnées", "Coordonnées GPS") +#define TR_VARIO TR("Vario", "Variomètre") +#define TR_PITCH_AT_ZERO INDENT "Tonalité au zéro" +#define TR_PITCH_AT_MAX INDENT "Tonalité au max" +#define TR_REPEAT_AT_ZERO TR(INDENT "Interv. au zéro", INDENT "Intervalle au zéro") +#define TR_POWEROFF "\037\120ARRET..." +#define TR_SHUTDOWN "ARRET EN COURS" +#define TR_SAVEMODEL "Sauvegarde modèle..." +#define TR_BATT_CALIB "Calib. batterie" +#define TR_CURRENT_CALIB "Calib. courant" +#define TR_VOLTAGE TR(INDENT "Tension",INDENT "Source tension") +#define TR_CURRENT TR(INDENT "Courant",INDENT "Source courant") +#define TR_SELECT_MODEL "Sélect. modèle" +#define TR_CREATE_CATEGORY "Créer une catégorie" +#define TR_RENAME_CATEGORY "Renommer la catégorie" +#define TR_DELETE_CATEGORY "Supprimer la catégorie" +#define TR_CREATE_MODEL "Créer modèle" +#define TR_DUPLICATE_MODEL "Dupliquer modèle" +#define TR_COPY_MODEL "Copier modèle" +#define TR_MOVE_MODEL "Déplacer modèle" +#define TR_BACKUP_MODEL "Archiver modèle" +#define TR_DELETE_MODEL "Supprimer modèle" +#define TR_RESTORE_MODEL "Restaurer modèle" +#define TR_DELETE_ERROR "Effacement impossible" +#define TR_CAT_NOT_EMPTY "Categorie non vide" +#define TR_SDCARD_ERROR "Erreur carte SD" +#define TR_NO_SDCARD "Carte SD indisponible" +#define TR_SDCARD_FULL "Carte SD pleine" +#define TR_INCOMPATIBLE "Incompatible" +#define TR_WARNING "ALERTE" +#define TR_EEPROMWARN "EEPROM" +#define TR_STORAGE_WARNING "STOCKAGE" +#define TR_EEPROM_CONVERTING "Conversion EEPROM" +#define TR_THROTTLEWARN "GAZ" +#define TR_ALARMSWARN "SON" +#define TR_SWITCHWARN TR("INTERS","CONTROLES") +#define TR_FAILSAFEWARN "FAILSAFE" +#define TR_NIGHTLY_WARNING TR("NIGHTLY", "NIGHTLY BUILD") +#define TR_NIGHTLY_NOTSAFE "Version de test uniq." +#define TR_WRONG_SDCARDVERSION "Version requise: " +#define TR_WRONG_PCBREV "PCB incorrect détecté" +#define TR_EMERGENCY_MODE "MODE SECOURS" +#define TR_PCBREV_ERROR "Erreur PCB" +#define TR_NO_FAILSAFE TR3("Failsafe pas déf.", "Failsafe pas déf.", "Failsafe pas défini") +#define TR_KEYSTUCK "Touche bloquée" +#define TR_INVERT_THR "Inverser gaz?" +#define TR_SPEAKER_VOLUME INDENT "Volume" +#define TR_LCD "Afficheur" +#define TR_BRIGHTNESS INDENT "Luminosité" +#define TR_CPU_TEMP "Temp. CPU\016>" +#define TR_CPU_CURRENT "Courant\022>" +#define TR_CPU_MAH "Consomm." +#define TR_COPROC "CoProc." +#define TR_COPROC_TEMP "Temp. MB \016>" +#define TR_CAPAWARNING INDENT "Capacité Basse" +#define TR_TEMPWARNING INDENT "Surchauffe" +#define TR_FUNC "Fonction" +#define TR_V1 "V1" +#define TR_V2 "V2" +#define TR_DURATION "Durée" +#define TR_DELAY "Délai" +#define TR_SD_CARD "Carte SD" +#define TR_SDHC_CARD "Carte SD-HC" +#define TR_NO_SOUNDS_ON_SD "Aucun son sur SD" +#define TR_NO_MODELS_ON_SD "Aucun modèle SD" +#define TR_NO_BITMAPS_ON_SD "Aucun Bitmap SD" +#define TR_NO_SCRIPTS_ON_SD "Aucun Script SD" +#define TR_SCRIPT_SYNTAX_ERROR "Erreur syntaxe script" +#define TR_SCRIPT_PANIC "Script bloqué" +#define TR_SCRIPT_KILLED "Script interrompu" +#define TR_SCRIPT_ERROR "Erreur inconnue" +#define TR_PLAY_FILE "Lire" +#define TR_DELETE_FILE "Supprimer" +#define TR_COPY_FILE "Copier" +#define TR_RENAME_FILE "Renommer" +#define TR_ASSIGN_BITMAP "Sélectionner image" +#define TR_EXECUTE_FILE "Exécuter" +#define TR_REMOVED " supprimé" +#define TR_SD_INFO "Information" +#define TR_SD_FORMAT "Formater" +#define TR_NA "N/D" +#define TR_HARDWARE "MATERIEL" +#define TR_FORMATTING "Formatage..." +#define TR_TEMP_CALIB "Calib. temp" +#define TR_TIME "Heure" +#define TR_MAXBAUDRATE "Max bauds" +#define TR_BLUETOOTH "Bluetooth" +#define TR_BAUDRATE "Baudrate BT" +#define LEN_BLUETOOTH_MODES "\012" +#define TR_BLUETOOTH_MODES "---\0 ""Télémétrie""Ecolage\0" +#define TR_SD_INFO_TITLE "INFO SD" +#define TR_SD_TYPE "Type:" +#define TR_SD_SPEED "Vitesse:" +#define TR_SD_SECTORS "Secteurs:" +#define TR_SD_SIZE "Taille:" +#define TR_TYPE INDENT "Type" +#define TR_GLOBAL_VARS "Variables Globales" +#define TR_GVARS "V. GLOBALES" +#define TR_GLOBAL_VAR "Variable globale" +#define TR_MENUGLOBALVARS "VARIABLES GLOBALES" +#define TR_OWN "Pers" +#define TR_DATE "Date" +#define TR_MONTHS { "Jan", "Fév", "Mar", "Avr", "Mai", "Jun", "Jul", "Aou", "Sep", "Oct", "Nov", "Dec" } +#define TR_ROTARY_ENCODER "Enc.Rot." +#define TR_CHANNELS_MONITOR "MONITEUR CANAUX" +#define TR_MIXERS_MONITOR "MONITEUR MIXAGES " +#define TR_PATH_TOO_LONG "Chemin trop long" +#define TR_VIEW_TEXT "Voir texte" +#define TR_FLASH_BOOTLOADER "Flasher BootLoader" +#define TR_FLASH_EXTERNAL_DEVICE TR("Flasher module ext.", "Flasher module externe") +#define TR_FLASH_INTERNAL_MODULE TR("Flasher module int.", "Flasher module interne") +#define TR_FIRMWARE_UPDATE_ERROR "Firmware update error" +#define TR_WRITING TR("\14Ecriture...", "\032Ecriture...") +#define TR_CONFIRM_FORMAT "Confirmer Formatage?" +#define TR_INTERNALRF "HF interne" +#define TR_EXTERNALRF "HF externe" +#define TR_FAILSAFE TR(INDENT "Failsafe", INDENT "Type failsafe") +#define TR_FAILSAFESET "REGLAGES FAILSAFE" +#define TR_HOLD "HOLD" +#define TR_NONE "NONE" +#define TR_MENUSENSOR "CAPTEUR" +#define TR_SENSOR "SENSOR" +#define TR_COUNTRYCODE TR("Zone géo.", "Zone géographique") +#define TR_USBMODE "USB Mode" +#define TR_VOICELANG TR("Langue voix", "Langue annonces vocales") +#define TR_UNITSSYSTEM "Unités" +#define TR_EDIT "Editer" +#define TR_INSERT_BEFORE "Insérer avant" +#define TR_INSERT_AFTER "Insérer après" +#define TR_COPY "Copier" +#define TR_MOVE "Déplacer" +#define TR_PASTE "Coller" +#define TR_DELETE "Supprimer" +#define TR_INSERT "Insérer" +#define TR_RESET_FLIGHT TR("Réinit. vol", "Réinitialiser vol") +#define TR_RESET_TIMER1 TR("Réinit. Timer1", "Réinitialiser Timer1") +#define TR_RESET_TIMER2 TR("Réinit. Timer2", "Réinitialiser Timer2") +#define TR_RESET_TIMER3 TR("Réinit. Timer3", "Réinitialiser Timer3") +#define TR_RESET_TELEMETRY TR("Réinit. Télém.", "Réinit. Télémétrie") +#define TR_STATISTICS "Statistiques" +#define TR_ABOUT_US "A propos" +#define TR_USB_JOYSTICK "USB Joystick (HID)" +#define TR_USB_MASS_STORAGE "Stockage USB (SD)" +#define TR_USB_SERIAL "Port série (Debug)" +#define TR_SETUP_SCREENS "Configuration écrans" +#define TR_MONITOR_SCREENS "Moniteurs" +#define TR_AND_SWITCH "ET suppl." +#define TR_SF "FS" +#define TR_GF "FG" +#define TR_SPEAKER INDENT "Haut-p." +#define TR_BUZZER INDENT "Bipeur" +#define TR_BYTES "bytes" +#define TR_MODULE_BIND BUTTON(TR("Bnd", "Bind")) +#define TR_MODULE_RANGE BUTTON(TR("Prt", "Port.")) +#define TR_RESET_BTN BUTTON("RAZ") +#define TR_SET BUTTON("Déf") +#define TR_TRAINER "Ecolage" +#define TR_ANTENNAPROBLEM CENTER "Antenne radio défectueuse!" +#define TR_MODELIDUSED TR("ID affecté à :", "No de récepteur utilisé par :") +#define TR_MODULE INDENT "Type de module" +#define TR_TELEMETRY_TYPE TR("Type tél.", "Type télémétrie") +#define TR_TELEMETRY_SENSORS "Capteurs" +#define TR_VALUE "Valeur" +#define TR_TOPLCDTIMER "Timer LCD haut" +#define TR_UNIT "Unité" +#define TR_TELEMETRY_NEWSENSOR TR(INDENT"Nouveau capteur...", INDENT "Ajout d'un nouveau capteur...") +#define TR_CHANNELRANGE TR(INDENT "Canaux", INDENT "Plage de canaux") +#define TR_ANTENNASELECTION INDENT "Choix antenne" +#define TR_ANTENNACONFIRM1 "Vraiment changer?" +#define TR_ANTENNACONFIRM2 "Installer l'antenne d'abord!" +#define TR_LOWALARM INDENT "Alarme basse" +#define TR_CRITICALALARM INDENT "Alarme critique" +#define TR_RSSIALARM_WARN TR("RSSI", "TELEMETRIE") +#define TR_NO_RSSIALARM TR(INDENT "Alarmes désact.", "Alarme télémétrie désactivée") +#define TR_DISABLE_ALARM TR(INDENT "Désact. alarme", INDENT "Désactiver alarme télémétrie") +#define TR_ENABLE_POPUP "Activer popup" +#define TR_DISABLE_POPUP "Désactiver popup" +#define TR_POPUP "Popup" +#define TR_MIN "Min" +#define TR_MAX "Max" +#define TR_CURVE_PRESET "Courbe standard..." +#define TR_PRESET "Pente" +#define TR_MIRROR "Miroir" +#define TR_CLEAR "Effacer" +#define TR_RESET "Réinitialiser" +#define TR_RESET_SUBMENU "Réinitialiser..." +#define TR_COUNT "Nb points" +#define TR_PT "pt" +#define TR_PTS "pts" +#define TR_SMOOTH "Lissage" +#define TR_COPY_STICKS_TO_OFS TR("Cpy stick->subtrim", "Manche vers subtrim") +#define TR_COPY_TRIMS_TO_OFS TR("Cpy trim->subtrim", "Trim vers subtrim") +#define TR_INCDEC "Inc/décrementer" +#define TR_GLOBALVAR "Var. globale" +#define TR_MIXSOURCE "Source mixeur" +#define TR_CONSTANT "Constante" +#define TR_PERSISTENT_MAH TR(INDENT "Enr. mAh", INDENT "Enregistrer mAh") +#define TR_PREFLIGHT "Vérifications avant vol" +#define TR_CHECKLIST TR(INDENT "Notes", INDENT "Afficher notes") +#define TR_FAS_OFFSET TR(INDENT "Corr FAS", INDENT "Correction FAS") +#define TR_UART3MODE "Port série" +#define TR_SCRIPT "Script" +#define TR_INPUTS "Entrées" +#define TR_OUTPUTS "Sorties" +#define TR_EEBACKUP TR("[ENTER Long]:Sauvegarde", "\004[ENTER Long]: Sauvegarder l'EEPROM") +#define TR_FACTORYRESET TR("\001[MENU Long]: RAZ d'usine", "\016[MENU Long]: RAZ d'usine") +#define TR_CONFIRMRESET TR("Effacer TOUT?","Effacer TOUS modèles/réglages?") +#define TR_TO_MANY_LUA_SCRIPTS "Trop de scripts lua!" #if defined(TELEMETRY_MAVLINK) #define TR_MAVLINK_RC_RSSI_SCALE_LABEL "RSSI Max" @@ -1114,211 +1159,211 @@ #define TR_LSW_HEADERS_DURATION "Durée min." #define TR_LSW_HEADERS_DELAY "Délai" -#define TR_GVAR_HEADERS_NAME "Name" -#define TR_GVAR_HEADERS_FM0 "Value on FM0" -#define TR_GVAR_HEADERS_FM1 "Value on FM1" -#define TR_GVAR_HEADERS_FM2 "Value on FM2" -#define TR_GVAR_HEADERS_FM3 "Value on FM3" -#define TR_GVAR_HEADERS_FM4 "Value on FM4" -#define TR_GVAR_HEADERS_FM5 "Value on FM5" -#define TR_GVAR_HEADERS_FM6 "Value on FM6" -#define TR_GVAR_HEADERS_FM7 "Value on FM7" -#define TR_GVAR_HEADERS_FM8 "Value on FM8" +#define TR_GVAR_HEADERS_NAME "Nom" +#define TR_GVAR_HEADERS_FM0 "Valeur FM0" +#define TR_GVAR_HEADERS_FM1 "Valeur FM1" +#define TR_GVAR_HEADERS_FM2 "Valeur FM2" +#define TR_GVAR_HEADERS_FM3 "Valeur FM3" +#define TR_GVAR_HEADERS_FM4 "Valeur FM4" +#define TR_GVAR_HEADERS_FM5 "Valeur FM5" +#define TR_GVAR_HEADERS_FM6 "Valeur FM6" +#define TR_GVAR_HEADERS_FM7 "Valeur FM7" +#define TR_GVAR_HEADERS_FM8 "Valeur FM8" // Horus footer descriptions -#define TR_LSW_DESCRIPTIONS { "Type de comparaison ou fonction", "Première variable", "Seconde variable ou constante", "Seconde variable ou constante", "Condition supplémentaire pour activer la ligne", "Durée minimale d'activation de l'inter logique", "Durée min de la condition avant l'activation de l'inter" } +#define TR_LSW_DESCRIPTIONS { "Type de comparaison ou fonction", "Première variable", "Seconde variable ou constante", "Seconde variable ou constante", "Condition supplémentaire pour activer la ligne", "Durée minimale d'activation de l'inter logique", "Durée min de la condition avant l'activation de l'inter" } // Taranis About screen -#define TR_ABOUTUS TR(" A PROPOS ", "A PROPOS") +#define TR_ABOUTUS TR(" A PROPOS ", "A PROPOS") -#define TR_ABOUT_OPENTX_1 TR("OpenTX\001est\001libre,\001non-", "OpenTX est libre, non-") -#define TR_ABOUT_OPENTX_2 TR("commercial,\001et\001offert\001sans", "commercial et n'offre aucune") -#define TR_ABOUT_OPENTX_3 TR("garantie.\001Il\001est\001développé", "garantie. Il a été développé") -#define TR_ABOUT_OPENTX_4 TR("gratuitement.\001Donations", "gratuitement. Vos donations") -#define TR_ABOUT_OPENTX_5 TR("bienvenues!", "sont bienvenues!") - -#define TR_ABOUT_BERTRAND_1 "Bertrand Songis" -#define TR_ABOUT_BERTRAND_2 TR("Auteur\001principal\001d'OpenTX", "Auteur principal d'OpenTX") -#define TR_ABOUT_BERTRAND_3 TR("Codéveloppeur\001de\001C9X", "Codéveloppeur de Companion") - -#define TR_ABOUT_MIKE_1 "Mike Blandford" -#define TR_ABOUT_MIKE_2 "Maître du code et des" -#define TR_ABOUT_MIKE_3 "drivers" -#define TR_ABOUT_MIKE_4 "" - -#define TR_ABOUT_ROMOLO_1 "Romolo Manfredini" -#define TR_ABOUT_ROMOLO_2 "Développeur principal de" -#define TR_ABOUT_ROMOLO_3 "OpenTX Companion" - -#define TR_ABOUT_ANDRE_1 "André Bernet" -#define TR_ABOUT_ANDRE_2 TR("Fonctionsé,\001usabilité,","Fonctionnalités, usabilité,") -#define TR_ABOUT_ANDRE_3 TR("débogage,\001documentation","débogage, documentation") - -#define TR_ABOUT_ROB_1 "Rob Thomson" -#define TR_ABOUT_ROB_2 "Webmaster d'openrcforums" - -#define TR_ABOUT_KJELL_1 "Kjell Kernen" -#define TR_ABOUT_KJELL_2 "Auteur de www.open-tx.org" -#define TR_ABOUT_KJELL_3 "Auteur de OpenTX Recorder" -#define TR_ABOUT_KJELL_4 "Développeur Companion" +#define TR_ABOUT_OPENTX_1 TR("OpenTX\001est\001libre,\001non-", "OpenTX est libre, non-") +#define TR_ABOUT_OPENTX_2 TR("commercial,\001et\001offert\001sans", "commercial et n'offre aucune") +#define TR_ABOUT_OPENTX_3 TR("garantie.\001Il\001est\001développé", "garantie. Il a été développé") +#define TR_ABOUT_OPENTX_4 TR("gratuitement.\001Donations", "gratuitement. Vos donations") +#define TR_ABOUT_OPENTX_5 TR("bienvenues!", "sont bienvenues!") + +#define TR_ABOUT_BERTRAND_1 "Bertrand Songis" +#define TR_ABOUT_BERTRAND_2 TR("Auteur\001principal\001d'OpenTX", "Auteur principal d'OpenTX") +#define TR_ABOUT_BERTRAND_3 TR("Codéveloppeur\001de\001C9X", "Codéveloppeur de Companion") + +#define TR_ABOUT_MIKE_1 "Mike Blandford" +#define TR_ABOUT_MIKE_2 "Maître du code et des" +#define TR_ABOUT_MIKE_3 "drivers" +#define TR_ABOUT_MIKE_4 "" + +#define TR_ABOUT_ROMOLO_1 "Romolo Manfredini" +#define TR_ABOUT_ROMOLO_2 "Développeur principal de" +#define TR_ABOUT_ROMOLO_3 "OpenTX Companion" + +#define TR_ABOUT_ANDRE_1 "André Bernet" +#define TR_ABOUT_ANDRE_2 TR("Fonctionsé,\001usabilité,","Fonctionnalités, usabilité,") +#define TR_ABOUT_ANDRE_3 TR("débogage,\001documentation","débogage, documentation") + +#define TR_ABOUT_ROB_1 "Rob Thomson" +#define TR_ABOUT_ROB_2 "Webmaster d'openrcforums" + +#define TR_ABOUT_KJELL_1 "Kjell Kernen" +#define TR_ABOUT_KJELL_2 "Auteur de www.open-tx.org" +#define TR_ABOUT_KJELL_3 "Auteur de OpenTX Recorder" +#define TR_ABOUT_KJELL_4 "Développeur Companion" -#define TR_ABOUT_MARTIN_1 "Martin Hotar" -#define TR_ABOUT_MARTIN_2 "Design graphique" +#define TR_ABOUT_MARTIN_1 "Martin Hotar" +#define TR_ABOUT_MARTIN_2 "Design graphique" #if defined(PCBTARANIS) - #define TR_ABOUT_HARDWARE_1 "FrSky" - #define TR_ABOUT_HARDWARE_2 "Développeur/fabricant" - #define TR_ABOUT_HARDWARE_3 "du matériel" -#else - #define TR_ABOUT_HARDWARE_1 "Brent Nelson" - #define TR_ABOUT_HARDWARE_2 "Développeur/fabricant" - #define TR_ABOUT_HARDWARE_3 "de la carte Sky9x" -#endif - -#define TR_ABOUT_PARENTS_1 "Projets parents" -#define TR_ABOUT_PARENTS_2 "ersky9x (Mike Blandford)" -#define TR_ABOUT_PARENTS_3 "ER9X (Erez Raviv)" -#define TR_ABOUT_PARENTS_4 "TH9X (Thomas Husterer)" - -#define TR_CHR_SHORT 's' -#define TR_CHR_LONG 'l' -#define TR_CHR_TOGGLE 't' -#define TR_CHR_HOUR 'h' -#define TR_CHR_INPUT 'E' // Values between A-I will work - -#define TR_BEEP_VOLUME "Volume bips" -#define TR_WAV_VOLUME "Volume audio" -#define TR_BG_VOLUME "Volume musique" - -#define TR_TOP_BAR "Barre titre" -#define TR_ALTITUDE INDENT "Altitude" -#define TR_SCALE "Echelle" -#define TR_VIEW_CHANNELS "Voir voies" -#define TR_VIEW_NOTES "Voir notes" -#define TR_MODEL_SELECT "Sélection modèle" -#define TR_MODS_FORBIDDEN "Modifications désactivées!" -#define TR_UNLOCKED "Déverrouillé" -#define TR_ID "ID" -#define TR_PRECISION "Précision" -#define TR_RATIO "Ratio" -#define TR_FORMULA "Formule" -#define TR_CELLINDEX "Index élem." -#define TR_LOGS "Logs" -#define TR_OPTIONS "Options" - -#define TR_ALTSENSOR "Capteur Alt" -#define TR_CELLSENSOR "Capteur Elém" -#define TR_GPSSENSOR "Capteur GPS" -#define TR_CURRENTSENSOR "Capteur" -#define TR_AUTOOFFSET "Offset auto" -#define TR_ONLYPOSITIVE "Positif" -#define TR_FILTER "Filtrage" -#define TR_TELEMETRYFULL "Plus de capteurs libres!" -#define TR_SERVOS_OK "Servos OK" -#define TR_SERVOS_KO "Servos KO" -#define TR_INVERTED_SERIAL INDENT "Inversé" -#define TR_IGNORE_INSTANCE TR(INDENT "Ign. inst", INDENT "Ignorer instance") -#define TR_DISCOVER_SENSORS INDENT "Découvrir capteurs" -#define TR_STOP_DISCOVER_SENSORS INDENT "Terminer découverte" -#define TR_DELETE_ALL_SENSORS TR(INDENT "Suppr. tous capteurs", INDENT "Supprimer tous capteurs") -#define TR_CONFIRMDELETE TR("Tout effacer?", "Vraiment tout " LCDW_128_480_LINEBREAK "effacer ?") -#define TR_SELECT_WIDGET "Sélect. widget" -#define TR_REMOVE_WIDGET "Supprimer widget" -#define TR_WIDGET_SETTINGS "Réglages widget" -#define TR_REMOVE_SCREEN "Supprimer écran" -#define TR_SETUP_WIDGETS "Configurer widgets" -#define TR_USER_INTERFACE "Interface utilisateur" -#define TR_THEME "Thème" -#define TR_SETUP "Configuration" -#define TR_MAINVIEWX "Vue principale X" -#define TR_LAYOUT "Disposition" -#define TR_ADDMAINVIEW "Ajouter vue principale" -#define TR_BACKGROUND_COLOR "Couleur de fond" -#define TR_MAIN_COLOR "Couleur principale" - -#define TR_MENU_INPUTS "\314Entrées" -#define TR_MENU_LUA "\322Scripts Lua" -#define TR_MENU_STICKS "\307Manches" -#define TR_MENU_POTS "\310Pots" -#define TR_MENU_MAX "\315MAX" -#define TR_MENU_HELI "\316Cyclique" -#define TR_MENU_TRIMS "\313Trims" -#define TR_MENU_SWITCHES "\312Inters" -#define TR_MENU_LOGICAL_SWITCHES "\312Inters logiques" -#define TR_MENU_TRAINER "\317Ecolage" -#define TR_MENU_CHANNELS "\320Canaux" -#define TR_MENU_GVARS "\311Vars. glob." -#define TR_MENU_TELEMETRY "\321Télémesure" -#define TR_MENU_DISPLAY "AFFICHAGE" -#define TR_MENU_OTHER "Autres" -#define TR_MENU_INVERT "Inverser" -#define TR_JITTER_FILTER "Filtre ADC" - -#define ZSTR_RSSI "RSSI" -#define ZSTR_SWR "SWR" -#define ZSTR_A1 "A1" -#define ZSTR_A2 "A2" -#define ZSTR_A3 "A3" -#define ZSTR_A4 "A4" -#define ZSTR_BATT "BtRx" -#define ZSTR_ALT "Alt" -#define ZSTR_TEMP1 "Tmp1" -#define ZSTR_TEMP2 "Tmp2" -#define ZSTR_RPM "RPM" -#define ZSTR_FUEL "Fuel" -#define ZSTR_VSPD "VSpd" -#define ZSTR_ACCX "AccX" -#define ZSTR_ACCY "AccY" -#define ZSTR_ACCZ "AccZ" -#define ZSTR_GYROX "GYRX" -#define ZSTR_GYROY "GYRY" -#define ZSTR_GYROZ "GYRZ" -#define ZSTR_CURR "Curr" -#define ZSTR_CAPACITY "Capa" -#define ZSTR_VFAS "VFAS" -#define ZSTR_ASPD "ASpd" -#define ZSTR_GSPD "GSpd" -#define ZSTR_HDG "Hdg" -#define ZSTR_SATELLITES "Sats" -#define ZSTR_CELLS "Cels" -#define ZSTR_GPSALT "GAlt" -#define ZSTR_GPSDATETIME "Date" -#define ZSTR_GPS "GPS" -#define ZSTR_BATT1_VOLTAGE "RB1V" -#define ZSTR_BATT2_VOLTAGE "RB2V" -#define ZSTR_BATT1_CURRENT "RB1A" -#define ZSTR_BATT2_CURRENT "RB2A" -#define ZSTR_BATT1_CONSUMPTION "RB1C" -#define ZSTR_BATT2_CONSUMPTION "RB2C" -#define ZSTR_BATT1_TEMP "RB1T" -#define ZSTR_BATT2_TEMP "RB2T" -#define ZSTR_RB_STATE "RBS" -#define ZSTR_CHANS_STATE "RBCS" -#define ZSTR_RX_RSSI1 "1RSS" -#define ZSTR_RX_RSSI2 "2RSS" -#define ZSTR_RX_QUALITY "RQly" -#define ZSTR_RX_SNR "RSNR" -#define ZSTR_RX_NOISE "RNse" -#define ZSTR_ANTENNA "ANT" -#define ZSTR_RF_MODE "RFMD" -#define ZSTR_TX_POWER "TPWR" -#define ZSTR_TX_RSSI "TRSS" -#define ZSTR_TX_QUALITY "TQly" -#define ZSTR_TX_SNR "TSNR" -#define ZSTR_TX_NOISE "TNse" -#define ZSTR_PITCH "Ptch" -#define ZSTR_ROLL "Roll" -#define ZSTR_YAW "Yaw" -#define ZSTR_FLIGHT_MODE "PV" -#define ZSTR_THROTTLE "Thr" -#define ZSTR_QOS_A "FdeA" -#define ZSTR_QOS_B "FdeB" -#define ZSTR_QOS_L "FdeL" -#define ZSTR_QOS_R "FdeR" -#define ZSTR_QOS_F "FLss" -#define ZSTR_QOS_H "Hold" -#define ZSTR_BIND "BIND" -#define ZSTR_LAP_NUMBER "Lap " -#define ZSTR_GATE_NUMBER "Gate" -#define ZSTR_LAP_TIME "LapT" -#define ZSTR_GATE_TIME "GteT" + #define TR_ABOUT_HARDWARE_1 "FrSky" + #define TR_ABOUT_HARDWARE_2 "Développeur/fabricant" + #define TR_ABOUT_HARDWARE_3 "du matériel" +#else + #define TR_ABOUT_HARDWARE_1 "Brent Nelson" + #define TR_ABOUT_HARDWARE_2 "Développeur/fabricant" + #define TR_ABOUT_HARDWARE_3 "de la carte Sky9x" +#endif + +#define TR_ABOUT_PARENTS_1 "Projets parents" +#define TR_ABOUT_PARENTS_2 "ersky9x (Mike Blandford)" +#define TR_ABOUT_PARENTS_3 "ER9X (Erez Raviv)" +#define TR_ABOUT_PARENTS_4 "TH9X (Thomas Husterer)" + +#define TR_CHR_SHORT 's' +#define TR_CHR_LONG 'l' +#define TR_CHR_TOGGLE 't' +#define TR_CHR_HOUR 'h' +#define TR_CHR_INPUT 'E' // Values between A-I will work + +#define TR_BEEP_VOLUME "Volume bips" +#define TR_WAV_VOLUME "Volume audio" +#define TR_BG_VOLUME "Volume musique" + +#define TR_TOP_BAR "Barre titre" +#define TR_ALTITUDE INDENT "Altitude" +#define TR_SCALE "Echelle" +#define TR_VIEW_CHANNELS "Voir voies" +#define TR_VIEW_NOTES "Voir notes" +#define TR_MODEL_SELECT "Sélection modèle" +#define TR_MODS_FORBIDDEN "Modifications désactivées!" +#define TR_UNLOCKED "Déverrouillé" +#define TR_ID "ID" +#define TR_PRECISION "Précision" +#define TR_RATIO "Ratio" +#define TR_FORMULA "Formule" +#define TR_CELLINDEX "Index élem." +#define TR_LOGS "Logs" +#define TR_OPTIONS "Options" + +#define TR_ALTSENSOR "Capteur Alt" +#define TR_CELLSENSOR "Capteur Elém" +#define TR_GPSSENSOR "Capteur GPS" +#define TR_CURRENTSENSOR "Capteur" +#define TR_AUTOOFFSET "Offset auto" +#define TR_ONLYPOSITIVE "Positif" +#define TR_FILTER "Filtrage" +#define TR_TELEMETRYFULL "Plus de capteurs libres!" +#define TR_SERVOS_OK "Servos OK" +#define TR_SERVOS_KO "Servos KO" +#define TR_INVERTED_SERIAL INDENT "Inversé" +#define TR_IGNORE_INSTANCE TR(INDENT "Ign. inst", INDENT "Ignorer instance") +#define TR_DISCOVER_SENSORS INDENT "Découvrir capteurs" +#define TR_STOP_DISCOVER_SENSORS INDENT "Terminer découverte" +#define TR_DELETE_ALL_SENSORS TR(INDENT "Suppr. tous capteurs", INDENT "Supprimer tous capteurs") +#define TR_CONFIRMDELETE TR("Tout effacer?", "Vraiment tout " LCDW_128_480_LINEBREAK "effacer ?") +#define TR_SELECT_WIDGET "Sélect. widget" +#define TR_REMOVE_WIDGET "Supprimer widget" +#define TR_WIDGET_SETTINGS "Réglages widget" +#define TR_REMOVE_SCREEN "Supprimer écran" +#define TR_SETUP_WIDGETS "Configurer widgets" +#define TR_USER_INTERFACE "Interface utilisateur" +#define TR_THEME "Thème" +#define TR_SETUP "Configuration" +#define TR_MAINVIEWX "Vue principale X" +#define TR_LAYOUT "Disposition" +#define TR_ADDMAINVIEW "Ajouter vue principale" +#define TR_BACKGROUND_COLOR "Couleur de fond" +#define TR_MAIN_COLOR "Couleur principale" + +#define TR_MENU_INPUTS "\314Entrées" +#define TR_MENU_LUA "\322Scripts Lua" +#define TR_MENU_STICKS "\307Manches" +#define TR_MENU_POTS "\310Pots" +#define TR_MENU_MAX "\315MAX" +#define TR_MENU_HELI "\316Cyclique" +#define TR_MENU_TRIMS "\313Trims" +#define TR_MENU_SWITCHES "\312Inters" +#define TR_MENU_LOGICAL_SWITCHES "\312Inters logiques" +#define TR_MENU_TRAINER "\317Ecolage" +#define TR_MENU_CHANNELS "\320Canaux" +#define TR_MENU_GVARS "\311Vars. glob." +#define TR_MENU_TELEMETRY "\321Télémétrie" +#define TR_MENU_DISPLAY "AFFICHAGE" +#define TR_MENU_OTHER "Autres" +#define TR_MENU_INVERT "Inverser" +#define TR_JITTER_FILTER "Filtre ADC" + +#define ZSTR_RSSI "RSSI" +#define ZSTR_SWR "SWR" +#define ZSTR_A1 "A1" +#define ZSTR_A2 "A2" +#define ZSTR_A3 "A3" +#define ZSTR_A4 "A4" +#define ZSTR_BATT "BtRx" +#define ZSTR_ALT "Alt" +#define ZSTR_TEMP1 "Tmp1" +#define ZSTR_TEMP2 "Tmp2" +#define ZSTR_RPM "RPM" +#define ZSTR_FUEL "Fuel" +#define ZSTR_VSPD "VSpd" +#define ZSTR_ACCX "AccX" +#define ZSTR_ACCY "AccY" +#define ZSTR_ACCZ "AccZ" +#define ZSTR_GYROX "GYRX" +#define ZSTR_GYROY "GYRY" +#define ZSTR_GYROZ "GYRZ" +#define ZSTR_CURR "Curr" +#define ZSTR_CAPACITY "Capa" +#define ZSTR_VFAS "VFAS" +#define ZSTR_ASPD "ASpd" +#define ZSTR_GSPD "GSpd" +#define ZSTR_HDG "Hdg" +#define ZSTR_SATELLITES "Sats" +#define ZSTR_CELLS "Cels" +#define ZSTR_GPSALT "GAlt" +#define ZSTR_GPSDATETIME "Date" +#define ZSTR_GPS "GPS" +#define ZSTR_BATT1_VOLTAGE "RB1V" +#define ZSTR_BATT2_VOLTAGE "RB2V" +#define ZSTR_BATT1_CURRENT "RB1A" +#define ZSTR_BATT2_CURRENT "RB2A" +#define ZSTR_BATT1_CONSUMPTION "RB1C" +#define ZSTR_BATT2_CONSUMPTION "RB2C" +#define ZSTR_BATT1_TEMP "RB1T" +#define ZSTR_BATT2_TEMP "RB2T" +#define ZSTR_RB_STATE "RBS" +#define ZSTR_CHANS_STATE "RBCS" +#define ZSTR_RX_RSSI1 "1RSS" +#define ZSTR_RX_RSSI2 "2RSS" +#define ZSTR_RX_QUALITY "RQly" +#define ZSTR_RX_SNR "RSNR" +#define ZSTR_RX_NOISE "RNse" +#define ZSTR_ANTENNA "ANT" +#define ZSTR_RF_MODE "RFMD" +#define ZSTR_TX_POWER "TPWR" +#define ZSTR_TX_RSSI "TRSS" +#define ZSTR_TX_QUALITY "TQly" +#define ZSTR_TX_SNR "TSNR" +#define ZSTR_TX_NOISE "TNse" +#define ZSTR_PITCH "Ptch" +#define ZSTR_ROLL "Roll" +#define ZSTR_YAW "Yaw" +#define ZSTR_FLIGHT_MODE "PV" +#define ZSTR_THROTTLE "Thr" +#define ZSTR_QOS_A "FdeA" +#define ZSTR_QOS_B "FdeB" +#define ZSTR_QOS_L "FdeL" +#define ZSTR_QOS_R "FdeR" +#define ZSTR_QOS_F "FLss" +#define ZSTR_QOS_H "Hold" +#define ZSTR_BIND "BIND" +#define ZSTR_LAP_NUMBER "Lap " +#define ZSTR_GATE_NUMBER "Gate" +#define ZSTR_LAP_TIME "LapT" +#define ZSTR_GATE_TIME "GteT" diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/translations/it.h.txt opentx-companion22-2.2.1~ppa01~xenial/radio/src/translations/it.h.txt --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/translations/it.h.txt 2017-05-31 19:49:19.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/translations/it.h.txt 2017-12-17 16:22:27.000000000 +0000 @@ -94,8 +94,11 @@ #define LEN_COUNTRYCODES TR("\002", "\007") #define TR_COUNTRYCODES TR("US""JP""EU", "America""Japan\0 ""Europa\0") +#define LEN_USBMODES TR("\006", "\010") +#define TR_USBMODES TR("Ask\0 ""Joyst\0""SDCard""Serial", "Ask\0 ""Joystick""Storage\0""Serial\0 ") + #define LEN_TARANIS_PROTOCOLS "\004" -#define TR_TARANIS_PROTOCOLS "OFF\0""PPM\0""XJT\0""DSM2""CRSF""MULT" +#define TR_TARANIS_PROTOCOLS "OFF\0""PPM\0""XJT\0""DSM2""CRSF""MULT""R9M\0""SBUS" #define LEN_TELEMETRY_PROTOCOLS "\017" #define TR_TELEMETRY_PROTOCOLS "FrSky S.PORT\0 ""FrSky D\0 ""FrSky D (cable)""TBS Crossfire\0 ""Spektrum\0 ""AFHDS2A IBUS\0 ""Multi Telemetry" @@ -107,7 +110,7 @@ #define TR_DSM_PROTOCOLS "LP45""DSM2""DSMX" #define LEN_MULTI_PROTOCOLS "\006" -#define TR_MULTI_PROTOCOLS "FlySky""Hubsan""FrSky\0""Hisky\0""V2x2\0 ""DSM\0 ""Devo\0 ""YD717\0""KN\0 ""SymaX\0""SLT\0 ""CX10\0 ""CG023\0""Bayang""ESky\0 ""MT99XX""MJXQ\0 ""Shenqi""FY326\0""SFHSS\0""J6 PRO""FQ777\0""Assan\0""Hontai""OLRS\0 ""FS 2A\0""Q2x2\0 ""Walk.\0""Q303\0 ""GW008\0""DM002\0" +#define TR_MULTI_PROTOCOLS "FlySky""Hubsan""FrSky\0""Hisky\0""V2x2\0 ""DSM\0 ""Devo\0 ""YD717\0""KN\0 ""SymaX\0""SLT\0 ""CX10\0 ""CG023\0""Bayang""ESky\0 ""MT99XX""MJXQ\0 ""Shenqi""FY326\0""SFHSS\0""J6 PRO""FQ777\0""Assan\0""Hontai""OLRS\0 ""FS 2A\0""Q2x2\0 ""Walk.\0""Q303\0 ""GW008\0""DM002\0""Cabell""Esky15""H8 3D\0" #define TR_MULTI_CUSTOM "Custom" @@ -438,9 +441,16 @@ #define LEN_GPSFORMAT "\004" #define TR_GPSFORMAT "HMS NMEA" -#define LEN2_VTEMPLATES 13 -#define LEN_VTEMPLATES "\015" -#define TR_VTEMPLATES "Canc. Mixer\0 ""Semplice 4CH\0""Sticky-T-Cut\0""Coda-V \0""Elevoni\0 ""Delta\0 ""eCCPM\0 ""Setup Heli\0 ""Test Servo\0 " +#define LEN2_VTEMPLATES 12 +#define LEN_VTEMPLATES "\014" +#define TR_TEMPLATE_CLEAR_MIXES "Canc. Mixer " +#define TR_TEMPLATE_SIMPLE_4CH "Semplice 4CH" +#define TR_TEMPLATE_STICKY_TCUT "Coda-V " +#define TR_TEMPLATE_VTAIL "V-Tail " +#define TR_TEMPLATE_DELTA "Elevon\\Delta" +#define TR_TEMPLATE_ECCPM "eCCPM " +#define TR_TEMPLATE_HELI "Heli Setup " +#define TR_TEMPLATE_SERVO_TEST "Test Servo " #define LEN_VSWASHTYPE "\004" #define TR_VSWASHTYPE "---\0""120\0""120X""140\0""90\0" @@ -552,6 +562,7 @@ #define TR_VTRAINER_MASTER_SBUS_MODULE "Master/Modulo SBUS" #define TR_VTRAINER_MASTER_CPPM_MODULE "Master/Modulo CPPM" #define TR_VTRAINER_MASTER_BATTERY "Master/Batteria\0 " +#define TR_VTRAINER_BLUETOOTH TR("Master/BT\0 ""Slave/BT\0", "Master/Bluetooth\0 ""Slave/Bluetooth\0 ") #define LEN_VFAILSAFE "\013" #define TR_VFAILSAFE "Non settato""Mantieni\0 ""Personali\0 ""No impulsi\0""Ricevente\0 " @@ -644,6 +655,8 @@ #define TR_PROTO TR(INDENT "Proto", INDENT "Protocollo") #if defined(CPUARM) #define TR_PPMFRAME INDENT "PPM frame" +#define TR_REFRESHRATE TR(INDENT "Refresh", INDENT "Refresh rate") +#define STR_WARN_BATTVOLTAGE TR(INDENT "Output is VBAT: ", INDENT "Warning: output level is VBAT: ") #else #define TR_PPMFRAME "PPM frame" #endif @@ -709,6 +722,9 @@ #define TR_INACTIVITYALARM INDENT"Inattivita'" #define TR_MEMORYWARNING INDENT"Avviso memoria" #define TR_ALARMWARNING INDENT"Spegni suono" +#define TR_RSSISHUTDOWNALARM TR(INDENT "Rssi Shutdown", INDENT "Check Rssi on Shutdown") +#define TR_MODEL_STILL_POWERED "Model still powered" +#define TR_PRESS_ENTER_TO_CONFIRM "Press enter to confirm" #define TR_RENAVIG "Navig EncRot " #define TR_THROTTLE_LABEL "Motore" #define TR_THROTTLEREVERSE TR("Mot inv.", INDENT "Motore Inverso") @@ -849,17 +865,25 @@ #define TR_MULTI_AUTOBIND TR(INDENT "Autobind",INDENT "Bind on powerup") #define TR_MULTI_DSM_AUTODTECT TR(INDENT "Autodetect", INDENT "Autodetect format") #define TR_MULTI_LOWPOWER TR(INDENT "Low power", INDENT "Low power mode") +#define TR_MODULE_TELEMETRY TR(INDENT "Mod telem.", INDENT "Module telemetry") #define TR_DISABLE_INTERNAL TR("Disable int. RF", "Disable internal RF") #define TR_MODULE_NO_SERIAL_MODE TR("!serial mode", "Not in serial mode") #define TR_MODULE_NO_INPUT TR("No input", "No serial input") #define TR_MODULE_NO_TELEMETRY TR3( "No telmetry", "No MULTI_TELEMETRY", "No telemetry (enable MULTI_TELEMETRY)") +#define TR_MODULE_WAITFORBIND "Bind to load protocol" #define TR_MODULE_BINDING "Binding" -#define TR_BINDING_MODE1 "Ch1-8 Telem ON" -#define TR_BINDING_MODE2 "Ch1-8 Telem OFF" -#define TR_BINDING_MODE3 "Ch9-16 Telem ON" -#define TR_BINDING_MODE4 "Ch9-16 Telem OFF" +#define TR_BINDING_CH1_8_TELEM_ON "Ch1-8 Telem ON" +#define TR_BINDING_CH1_8_TELEM_OFF "Ch1-8 Telem OFF" +#define TR_BINDING_CH9_16_TELEM_ON "Ch9-16 Telem ON" +#define TR_BINDING_CH9_16_TELEM_OFF "Ch9-16 Telem OFF" +#define TR_BINDING_25MW_CH1_8_TELEM_OFF TR("25mW Ch1-8 Tel OFF", "25mW Ch1-8 Telem OFF") +#define TR_BINDING_25MW_CH1_8_TELEM_ON TR("25mW Ch1-8 Tel ON", "25mW Ch1-8 Telem ON") +#define TR_BINDING_500MW_CH1_8_TELEM_OFF TR("500mW Ch1-8 Tel OFF", "500mW Ch1-8 Telem OFF") +#define TR_BINDING_500MW_CH9_16_TELEM_OFF TR("500mW Ch9-16 Tel OFF", "500mW Ch9-16 Telem OFF") +#define TR_BINDING_OPTION "Set at bind" #define TR_PROTOCOL_INVALID TR("Prot. invalid", "Protocol invalid") #define TR_MODULE_STATUS TR(INDENT "Status", INDENT "Module Status") +#define TR_MODULE_SYNC TR(INDENT "Sync", INDENT "Module Sync") #define TR_MULTI_SERVOFREQ TR(INDENT "Servo rate", INDENT "Servo update rate") #define TR_SYNCMENU "[Sync]" #define TR_LIMIT INDENT "Limiti" @@ -903,6 +927,8 @@ #define TR_ALARMSWARN "ALLARMI" #define TR_SWITCHWARN "CONTROLLI" #define TR_FAILSAFEWARN "FAILSAFE" +#define TR_NIGHTLY_WARNING TR("NIGHTLY", "NIGHTLY BUILD") +#define TR_NIGHTLY_NOTSAFE "Version not safe to fly" #define TR_WRONG_SDCARDVERSION TR("Expected ver: ","Expected version: ") #define TR_WRONG_PCBREV "Wrong PCB detected" #define TR_EMERGENCY_MODE "EMERGENCY MODE" @@ -949,7 +975,13 @@ #define TR_FORMATTING "Formattazione." #define TR_TEMP_CALIB "Temp. Calib" #define TR_TIME "Ora" +#define TR_MAXBAUDRATE "Max bauds" + +#define TR_BLUETOOTH "Bluetooth" #define TR_BAUDRATE "BT Baudrate" +#define LEN_BLUETOOTH_MODES "\011" +#define TR_BLUETOOTH_MODES "---\0 ""Telemetry""Trainer\0" + #define TR_SD_INFO_TITLE "SD INFO" #define TR_SD_TYPE "Tipo:" #define TR_SD_SPEED "Veloc.:" @@ -983,6 +1015,7 @@ #define TR_MENUSENSOR "SENSOR" #define TR_SENSOR "SENSOR" #define TR_COUNTRYCODE TR("Codice Paese","Standard 2.4Ghz") +#define TR_USBMODE "USB Mode" #define TR_VOICELANG "Lingua Voce" #define TR_UNITSSYSTEM "Unità" #define TR_EDIT "Modifica" @@ -1000,7 +1033,10 @@ #define TR_RESET_TELEMETRY "Azzera Telemetria" #define TR_STATISTICS "Statistiche" #define TR_ABOUT_US "Info su" -#define TR_SETUP_SCREENS "Setup screens" +#define TR_USB_JOYSTICK "USB Joystick (HID)" +#define TR_USB_MASS_STORAGE "USB Storage (SD)" +#define TR_USB_SERIAL "USB Serial (Debug)" +#define TR_SETUP_SCREENS "Setup screens" #define TR_MONITOR_SCREENS "Monitors" #define TR_AND_SWITCH "Inter. AND" #define TR_SF "CF" @@ -1028,6 +1064,9 @@ #define TR_ANTENNACONFIRM2 "Make sure antenna is installed!" #define TR_LOWALARM INDENT "Allarme Basso" #define TR_CRITICALALARM INDENT "Allarme Critico" +#define TR_RSSIALARM_WARN TR("RSSI","TELEMETRY RSSI") +#define TR_NO_RSSIALARM TR(INDENT "Alarms disabled", INDENT "Telemetry alarms disabled") +#define TR_DISABLE_ALARM TR(INDENT "Disable alarms", INDENT "Disable telemetry alarms") #define TR_ENABLE_POPUP "Abilita Popup" #define TR_DISABLE_POPUP "Disabilita Popup" #define TR_POPUP "Popup" diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/translations/nl.h.txt opentx-companion22-2.2.1~ppa01~xenial/radio/src/translations/nl.h.txt --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/translations/nl.h.txt 2017-05-31 19:49:19.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/translations/nl.h.txt 2017-12-17 16:22:27.000000000 +0000 @@ -99,8 +99,11 @@ #define LEN_COUNTRYCODES TR("\002", "\007") #define TR_COUNTRYCODES TR("US""JP""EU", "Amerika""Japan\0 ""Europa\0") +#define LEN_USBMODES TR("\006", "\010") +#define TR_USBMODES TR("Ask\0 ""Joyst\0""SDCard""Serial", "Ask\0 ""Joystick""Storage\0""Serial\0 ") + #define LEN_TARANIS_PROTOCOLS "\004" -#define TR_TARANIS_PROTOCOLS "UIT\0""PPM\0""XJT\0""DSM2""CRSF""MULT" +#define TR_TARANIS_PROTOCOLS "UIT\0""PPM\0""XJT\0""DSM2""CRSF""MULT""R9M\0""SBUS" #define LEN_TELEMETRY_PROTOCOLS "\017" #define TR_TELEMETRY_PROTOCOLS "FrSky S.PORT\0 ""FrSky D\0 ""FrSky D (cable)""TBS Crossfire\0 ""Spektrum\0 ""AFHDS2A IBUS\0 ""Multi Telemetry" @@ -112,7 +115,7 @@ #define TR_DSM_PROTOCOLS "LP45""DSM2""DSMX" #define LEN_MULTI_PROTOCOLS "\006" -#define TR_MULTI_PROTOCOLS "FlySky""Hubsan""FrSky\0""Hisky\0""V2x2\0 ""DSM\0 ""Devo\0 ""YD717\0""KN\0 ""SymaX\0""SLT\0 ""CX10\0 ""CG023\0""Bayang""ESky\0 ""MT99XX""MJXQ\0 ""Shenqi""FY326\0""SFHSS\0""J6 PRO""FQ777\0""Assan\0""Hontai""OLRS\0 ""FS 2A\0""Q2x2\0 ""Walk.\0""Q303\0 ""GW008\0""DM002\0" +#define TR_MULTI_PROTOCOLS "FlySky""Hubsan""FrSky\0""Hisky\0""V2x2\0 ""DSM\0 ""Devo\0 ""YD717\0""KN\0 ""SymaX\0""SLT\0 ""CX10\0 ""CG023\0""Bayang""ESky\0 ""MT99XX""MJXQ\0 ""Shenqi""FY326\0""SFHSS\0""J6 PRO""FQ777\0""Assan\0""Hontai""OLRS\0 ""FS 2A\0""Q2x2\0 ""Walk.\0""Q303\0 ""GW008\0""DM002\0""Cabell""Esky15""H8 3D\0" #define TR_MULTI_CUSTOM "Custom" @@ -413,12 +416,19 @@ #define LEN_GPSFORMAT "\004" #define TR_GPSFORMAT "DMS\0""NMEA" -#define LEN2_VTEMPLATES 13 -#define LEN_VTEMPLATES "\015" -#define TR_VTEMPLATES "Mix wissen\0\0\0""Simple 4-CH \0""Sticky-T-Cut\0""V-Tail \0""Elevon\\Delta\0""eCCPM \0""Heli Setup \0""Servo Test \0" +#define LEN2_VTEMPLATES 12 +#define LEN_VTEMPLATES "\014" +#define TR_TEMPLATE_CLEAR_MIXES "Mix wissen " +#define TR_TEMPLATE_SIMPLE_4CH "Simple 4-CH " +#define TR_TEMPLATE_STICKY_TCUT "Sticky-T-Cut" +#define TR_TEMPLATE_VTAIL "V-Tail " +#define TR_TEMPLATE_DELTA "Elevon\\Delta" +#define TR_TEMPLATE_ECCPM "eCCPM " +#define TR_TEMPLATE_HELI "Heli Setup " +#define TR_TEMPLATE_SERVO_TEST "Servo Test " -#define LEN_VSWASHTYPE "\004" -#define TR_VSWASHTYPE "---\0""120\0""120X""140\0""90\0" +#define LEN_VSWASHTYPE "\004" +#define TR_VSWASHTYPE "---\0""120\0""120X""140\0""90\0" #if defined(PCBHORUS) #define LEN_VKEYS "\006" @@ -543,7 +553,8 @@ #define TR_VTRAINER_SLAVE_JACK "Slave/Jack\0 " #define TR_VTRAINER_MASTER_SBUS_MODULE "Master/SBUS Module" #define TR_VTRAINER_MASTER_CPPM_MODULE "Master/CPPM Module" -#define TR_VTRAINER_MASTER_BATTERY "Master/Battery\0" +#define TR_VTRAINER_MASTER_BATTERY "Master/Battery\0 " +#define TR_VTRAINER_BLUETOOTH TR("Master/BT\0 ""Slave/BT\0", "Master/Bluetooth\0 ""Slave/Bluetooth\0 ") #define LEN_VFAILSAFE TR("\013","\011") #define TR_VFAILSAFE TR("Niet Gezet\0""Vasthouden\0""Custom\0 ""Geen Pulsen""Ontvanger\0 ","Not Set\0 ""Hold\0 ""Custom\0 ""No Pulses""Receiver\0") @@ -635,6 +646,8 @@ #define TR_PROTO TR(INDENT "Proto", INDENT "Protocol") #if defined(CPUARM) #define TR_PPMFRAME INDENT "PPM frame" +#define TR_REFRESHRATE TR(INDENT "Refresh", INDENT "Refresh rate") +#define STR_WARN_BATTVOLTAGE TR(INDENT "Output is VBAT: ", INDENT "Warning: output level is VBAT: ") #else #define TR_PPMFRAME "PPM frame" #endif @@ -688,28 +701,31 @@ #define TR_BLADES "Bladen" #define TR_SCREEN "Scherm\001" -#define TR_SOUND_LABEL "----Geluid-------" +#define TR_SOUND_LABEL "Geluid-" #define TR_LENGTH INDENT "Duur" #define TR_BEEP_LENGTH INDENT "Piep-Lengte" #define TR_SPKRPITCH INDENT "Piep-Freq. +/-" -#define TR_HAPTIC_LABEL "----Haptic-------" //9XR-Pro +#define TR_HAPTIC_LABEL "Haptic" #define TR_HAPTICSTRENGTH INDENT "Sterkte" #define TR_CONTRAST "LCD-Kontrast" -#define TR_ALARMS_LABEL "----Alarm---" +#define TR_ALARMS_LABEL "Alarm" #define TR_BATTERY_RANGE TR("Accu Bereik", "Accu Spngs-Bereik") // Symbol Akku Ladezustand #define TR_BATTERYWARNING INDENT "Accu laag" #define TR_INACTIVITYALARM TR(INDENT "Inactiviteit", INDENT "Inactiviteit na") //9XR-Pro #define TR_MEMORYWARNING INDENT "Geheugen laag" #define TR_ALARMWARNING TR(INDENT "Al Geluid uit?", INDENT "Al het geluid uit?") +#define TR_RSSISHUTDOWNALARM TR(INDENT "Rssi Shutdown", INDENT "Check Rssi on Shutdown") +#define TR_MODEL_STILL_POWERED "Model still powered" +#define TR_PRESS_ENTER_TO_CONFIRM "Press enter to confirm" #define TR_RENAVIG "Stappenschakelaar" -#define TR_THROTTLE_LABEL "----Gas-------------" +#define TR_THROTTLE_LABEL "Gas" #define TR_THROTTLEREVERSE TR("Reverse", INDENT "Omgekeerd") #define TR_TIMER_NAME INDENT "Naam" #define TR_MINUTEBEEP TR(INDENT "Min-Alarm", INDENT "Minuten-Alarm") #define TR_BEEPCOUNTDOWN INDENT "Countdown" #define TR_PERSISTENT TR(INDENT "Vasth.", INDENT "Vasthouden") -#define TR_BACKLIGHT_LABEL "----LCD-Verlichting--" +#define TR_BACKLIGHT_LABEL "LCD-Verlichting" #define TR_BLDELAY INDENT "Duur" #define TR_BLONBRIGHTNESS INDENT "Aan-Helderheid" #define TR_BLOFFBRIGHTNESS INDENT "Uit-Helderheid" @@ -722,7 +738,7 @@ #define TR_POTWARNING TR(IF_CPUARM(INDENT) "Pot Warn.", INDENT "Pot Posities") #define TR_TIMEZONE TR("Tijdzone", "GPS-Tijdzone +/-Std") #define TR_ADJUST_RTC TR("Klok instellen", INDENT "Klok middels GPS instellen") -#define TR_GPS "----GPS--------------" +#define TR_GPS "GPS" #define TR_RXCHANNELORD TR("Kan.Volgorde", "Kanaalvolgorde") #define TR_STICKS "Sticks" #define TR_POTS "Pots" @@ -847,17 +863,25 @@ #define TR_MULTI_AUTOBIND TR(INDENT "Autobind",INDENT "Bind on powerup") #define TR_MULTI_DSM_AUTODTECT TR(INDENT "Autodetect", INDENT "Autodetect format") #define TR_MULTI_LOWPOWER TR(INDENT "Low power", INDENT "Low power mode") +#define TR_MODULE_TELEMETRY TR(INDENT "Mod telem.", INDENT "Module telemetry") #define TR_DISABLE_INTERNAL TR("Disable int. RF", "Disable internal RF") #define TR_MODULE_NO_SERIAL_MODE TR("!serial mode", "Not in serial mode") #define TR_MODULE_NO_INPUT TR("No input", "No serial input") #define TR_MODULE_NO_TELEMETRY TR3( "No telmetry", "No MULTI_TELEMETRY", "No telemetry (enable MULTI_TELEMETRY)") +#define TR_MODULE_WAITFORBIND "Bind to load protocol" #define TR_MODULE_BINDING "Binding" -#define TR_BINDING_MODE1 "Ch1-8 Telem ON" -#define TR_BINDING_MODE2 "Ch1-8 Telem OFF" -#define TR_BINDING_MODE3 "Ch9-16 Telem ON" -#define TR_BINDING_MODE4 "Ch9-16 Telem OFF" +#define TR_BINDING_CH1_8_TELEM_ON "Ch1-8 Telem ON" +#define TR_BINDING_CH1_8_TELEM_OFF "Ch1-8 Telem OFF" +#define TR_BINDING_CH9_16_TELEM_ON "Ch9-16 Telem ON" +#define TR_BINDING_CH9_16_TELEM_OFF "Ch9-16 Telem OFF" +#define TR_BINDING_25MW_CH1_8_TELEM_OFF TR("25mW Ch1-8 Tel OFF", "25mW Ch1-8 Telem OFF") +#define TR_BINDING_25MW_CH1_8_TELEM_ON TR("25mW Ch1-8 Tel ON", "25mW Ch1-8 Telem ON") +#define TR_BINDING_500MW_CH1_8_TELEM_OFF TR("500mW Ch1-8 Tel OFF", "500mW Ch1-8 Telem OFF") +#define TR_BINDING_500MW_CH9_16_TELEM_OFF TR("500mW Ch9-16 Tel OFF", "500mW Ch9-16 Telem OFF") +#define TR_BINDING_OPTION "Set at bind" #define TR_PROTOCOL_INVALID TR("Prot. invalid", "Protocol invalid") #define TR_MODULE_STATUS TR(INDENT "Status", INDENT "Module Status") +#define TR_MODULE_SYNC TR(INDENT "Sync", INDENT "Module Sync") #define TR_MULTI_SERVOFREQ TR(INDENT "Servo rate", INDENT "Servo update rate") #define TR_SYNCMENU "Sync [MENU]" #define TR_LIMIT INDENT "Grenzen" @@ -865,7 +889,7 @@ #define TR_LATITUDE "Latitude" #define TR_LONGITUDE "Longitude" #define TR_GPSCOORD TR("GPS-coord.", "GPS-coordinaten format") -#define TR_VARIO TR("----Vario--------", "----Variometer----") //9XR-Pro +#define TR_VARIO "Variometer" #define TR_PITCH_AT_ZERO INDENT "Laagste Toon" #define TR_PITCH_AT_MAX INDENT "Hoogste Toon" #define TR_REPEAT_AT_ZERO INDENT "Herhalen bij 0" @@ -901,6 +925,8 @@ #define TR_ALARMSWARN "ALARM" #define TR_SWITCHWARN "SCHAKELAAR" #define TR_FAILSAFEWARN "FAILSAFE" +#define TR_NIGHTLY_WARNING TR("NIGHTLY", "NIGHTLY BUILD") +#define TR_NIGHTLY_NOTSAFE "Version not safe to fly" #define TR_WRONG_SDCARDVERSION TR("Verwachte ver: ","Verwachte versie: ") #define TR_WRONG_PCBREV "Verkeerde PCB gedetecteerd" #define TR_EMERGENCY_MODE "EMERGENCY MODE" @@ -947,7 +973,13 @@ #define TR_FORMATTING "Formatteren..." #define TR_TEMP_CALIB "Temp. Calib." #define TR_TIME "Tijd:" +#define TR_MAXBAUDRATE "Max bauds" + +#define TR_BLUETOOTH "Bluetooth" #define TR_BAUDRATE "BT Baudrate" +#define LEN_BLUETOOTH_MODES "\011" +#define TR_BLUETOOTH_MODES "---\0 ""Telemetry""Trainer\0" + #define TR_SD_INFO_TITLE "SD-INFO" #define TR_SD_TYPE "Type:" #define TR_SD_SPEED "Snelheid:" @@ -981,6 +1013,7 @@ #define TR_MENUSENSOR "SENSOR" #define TR_SENSOR "SENSOR" #define TR_COUNTRYCODE "Landcode" +#define TR_USBMODE "USB Mode" #define TR_VOICELANG "Taal" #define TR_UNITSSYSTEM "Eenheden" #define TR_EDIT "Wijzigen" @@ -998,7 +1031,10 @@ #define TR_RESET_TELEMETRY "Reset Telemetrie" #define TR_STATISTICS "Statistieken" #define TR_ABOUT_US "De Programmeurs" -#define TR_SETUP_SCREENS "Setup screens" +#define TR_USB_JOYSTICK "USB Joystick (HID)" +#define TR_USB_MASS_STORAGE "USB Storage (SD)" +#define TR_USB_SERIAL "USB Serial (Debug)" +#define TR_SETUP_SCREENS "Setup screens" #define TR_MONITOR_SCREENS "Monitors" #define TR_AND_SWITCH "AND Switch" #define TR_SF "SF" @@ -1015,7 +1051,7 @@ #define TR_MODELIDUSED TR("ID al gebruikt", "Model-ID al gebruikt") #define TR_MODULE INDENT "Module-Type" #define TR_TELEMETRY_TYPE TR("Type", "Telemetrietype") -#define TR_TELEMETRY_SENSORS "----Sensoren----" +#define TR_TELEMETRY_SENSORS "Sensoren" #define TR_VALUE "Waarde" #define TR_TOPLCDTIMER "Top LCD Timer" #define TR_UNIT "Eenheid" @@ -1026,6 +1062,9 @@ #define TR_ANTENNACONFIRM2 "Is er zeker een antenne geplaatst!" #define TR_LOWALARM INDENT "Waarschuwing" #define TR_CRITICALALARM INDENT "Kritiek Alarm" +#define TR_RSSIALARM_WARN TR("RSSI","TELEMETRY RSSI") +#define TR_NO_RSSIALARM TR(INDENT "Alarms disabled", INDENT "Telemetry alarms disabled") +#define TR_DISABLE_ALARM TR(INDENT "Disable alarms", INDENT "Disable telemetry alarms") #define TR_ENABLE_POPUP "Inschakelen Popups" #define TR_DISABLE_POPUP "Uitschakelen Popups" #define TR_POPUP "Popup" @@ -1199,7 +1238,7 @@ #define TR_WAV_VOLUME "Wav-Volume" #define TR_BG_VOLUME "Achtergr-Volume" -#define TR_TOP_BAR "-------Info------" +#define TR_TOP_BAR "Info" #define TR_ALTITUDE INDENT "Hoogte" #define TR_SCALE "Schaal" #define TR_VIEW_CHANNELS "Toon Kanalen" diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/translations/pl.h.txt opentx-companion22-2.2.1~ppa01~xenial/radio/src/translations/pl.h.txt --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/translations/pl.h.txt 2017-05-31 19:49:19.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/translations/pl.h.txt 2017-12-17 16:22:27.000000000 +0000 @@ -95,8 +95,11 @@ #define LEN_COUNTRYCODES TR("\002", "\007") #define TR_COUNTRYCODES TR("US""JP""EU", "Ameryka""Japonia""Europa\0") +#define LEN_USBMODES TR("\006", "\010") +#define TR_USBMODES TR("Ask\0 ""Joyst\0""SDCard""Serial", "Ask\0 ""Joystick""Storage\0""Serial\0 ") + #define LEN_TARANIS_PROTOCOLS "\004" -#define TR_TARANIS_PROTOCOLS "OFF\0""PPM\0""XJT\0""DSM2""CRSF""MULT" +#define TR_TARANIS_PROTOCOLS "OFF\0""PPM\0""XJT\0""DSM2""CRSF""MULT""R9M\0""SBUS" #define LEN_TELEMETRY_PROTOCOLS "\017" #define TR_TELEMETRY_PROTOCOLS "FrSky S.PORT\0 ""FrSky D\0 ""FrSky D (cable)""TBS Crossfire\0 ""Spektrum\0 ""AFHDS2A IBUS\0 ""Multi Telemetry" @@ -108,7 +111,7 @@ #define TR_DSM_PROTOCOLS "LP45""DSM2""DSMX" #define LEN_MULTI_PROTOCOLS "\006" -#define TR_MULTI_PROTOCOLS "FlySky""Hubsan""FrSky\0""Hisky\0""V2x2\0 ""DSM\0 ""Devo\0 ""YD717\0""KN\0 ""SymaX\0""SLT\0 ""CX10\0 ""CG023\0""Bayang""ESky\0 ""MT99XX""MJXQ\0 ""Shenqi""FY326\0""SFHSS\0""J6 PRO""FQ777\0""Assan\0""Hontai""OLRS\0 ""FS 2A\0""Q2x2\0 ""Walk.\0""Q303\0 ""GW008\0""DM002\0" +#define TR_MULTI_PROTOCOLS "FlySky""Hubsan""FrSky\0""Hisky\0""V2x2\0 ""DSM\0 ""Devo\0 ""YD717\0""KN\0 ""SymaX\0""SLT\0 ""CX10\0 ""CG023\0""Bayang""ESky\0 ""MT99XX""MJXQ\0 ""Shenqi""FY326\0""SFHSS\0""J6 PRO""FQ777\0""Assan\0""Hontai""OLRS\0 ""FS 2A\0""Q2x2\0 ""Walk.\0""Q303\0 ""GW008\0""DM002\0""Cabell""Esky15""H8 3D\0" #define TR_MULTI_CUSTOM "Custom" @@ -442,7 +445,14 @@ #define LEN2_VTEMPLATES 13 #define LEN_VTEMPLATES "\015" /*13 decimal*/ -#define TR_VTEMPLATES "Usuń Miksy ""Prosty. 4kn\0 ""Przełą-T-Cut\0""V-Tail \0""Elevon-Delta\0""eCCPM \0""Ustaw Heli \0""Test serwa \0" +#define TR_TEMPLATE_CLEAR_MIXES "Usuń Miksy " +#define TR_TEMPLATE_SIMPLE_4CH "Prosty. 4kn\0 " +#define TR_TEMPLATE_STICKY_TCUT "Przełą-T-Cut\0" +#define TR_TEMPLATE_VTAIL "V-Tail " +#define TR_TEMPLATE_DELTA "Elevon\\Delta " +#define TR_TEMPLATE_ECCPM "eCCPM " +#define TR_TEMPLATE_HELI "Ustaw Heli \0" +#define TR_TEMPLATE_SERVO_TEST "Test serwa \0" #define LEN_VSWASHTYPE "\004" #define TR_VSWASHTYPE "---\0""120\0""120X""140\0""90\0" @@ -554,6 +564,7 @@ #define TR_VTRAINER_MASTER_SBUS_MODULE "Trener/SBUS Moduł " #define TR_VTRAINER_MASTER_CPPM_MODULE "Trener/CPPM Moduł " #define TR_VTRAINER_MASTER_BATTERY "Trener/Bateria\0 " +#define TR_VTRAINER_BLUETOOTH TR("Master/BT\0 ""Slave/BT\0", "Master/Bluetooth\0 ""Slave/Bluetooth\0 ") #define LEN_VFAILSAFE "\011" /*9 decimal*/ #define TR_VFAILSAFE "Brak \0 ""Utrzymuj\0""Własne \0""0 sygnału""Odbiornik" @@ -646,6 +657,8 @@ #define TR_PROTO TR(INDENT "Proto", INDENT "Protokół") #if defined(CPUARM) #define TR_PPMFRAME INDENT "Ramka PPM" +#define TR_REFRESHRATE TR(INDENT "Refresh", INDENT "Refresh rate") +#define STR_WARN_BATTVOLTAGE TR(INDENT "Output is VBAT: ", INDENT "Warning: output level is VBAT: ") #else #define TR_PPMFRAME INDENT "Ramka PPM" #endif @@ -711,6 +724,9 @@ #define TR_INACTIVITYALARM INDENT"Alarm bezczynności" #define TR_MEMORYWARNING INDENT"Pełna pamięć" #define TR_ALARMWARNING INDENT"Wyłącz dźwięk" +#define TR_RSSISHUTDOWNALARM TR(INDENT "Rssi Shutdown", INDENT "Check Rssi on Shutdown") +#define TR_MODEL_STILL_POWERED "Model still powered" +#define TR_PRESS_ENTER_TO_CONFIRM "Press enter to confirm" #define TR_RENAVIG "Nawigacja potencjometrem" #define TR_THROTTLE_LABEL "Gaz " #define TR_THROTTLEREVERSE TR("OdwrGaz", INDENT "OdwrGaz") @@ -837,10 +853,11 @@ #define TR_MONITOR_OUTPUT_DESC "Outputs" #define TR_MONITOR_MIXER_DESC "Mixers" #if defined(CPUARM) - #define TR_RECEIVER_NUM TR( INDENT "Nr RX",INDENT "Nr odbiornika") -#define TR_RECEIVER INDENT "Receiver" + #define TR_RECEIVER_NUM TR( INDENT "Nr RX",INDENT "Nr odbiornika") + #define TR_RECEIVER INDENT "Receiver" #else - #define TR_RECEIVER_NUM "NumOdb" + #define TR_RECEIVER_NUM "NumOdb" + #define TR_RECEIVER INDENT "Receiver" #endif #define TR_MULTI_RFTUNE TR(INDENT "Freq tune",INDENT "RF Freq. fine tune") #define TR_MULTI_TELEMETRY "Telemetry" @@ -850,17 +867,25 @@ #define TR_MULTI_AUTOBIND TR(INDENT "Autobind",INDENT "Bind on powerup") #define TR_MULTI_DSM_AUTODTECT TR(INDENT "Autodetect", INDENT "Autodetect format") #define TR_MULTI_LOWPOWER TR(INDENT "Low power", INDENT "Low power mode") +#define TR_MODULE_TELEMETRY TR(INDENT "Mod telem.", INDENT "Module telemetry") #define TR_DISABLE_INTERNAL TR("Disable int. RF", "Disable internal RF") #define TR_MODULE_NO_SERIAL_MODE TR("!serial mode", "Not in serial mode") #define TR_MODULE_NO_INPUT TR("No input", "No serial input") #define TR_MODULE_NO_TELEMETRY TR3( "No telmetry", "No MULTI_TELEMETRY", "No telemetry (enable MULTI_TELEMETRY)") +#define TR_MODULE_WAITFORBIND "Bind to load protocol" #define TR_MODULE_BINDING "Binding" -#define TR_BINDING_MODE1 "Ch1-8 Telem ON" -#define TR_BINDING_MODE2 "Ch1-8 Telem OFF" -#define TR_BINDING_MODE3 "Ch9-16 Telem ON" -#define TR_BINDING_MODE4 "Ch9-16 Telem OFF" +#define TR_BINDING_CH1_8_TELEM_ON "Ch1-8 Telem ON" +#define TR_BINDING_CH1_8_TELEM_OFF "Ch1-8 Telem OFF" +#define TR_BINDING_CH9_16_TELEM_ON "Ch9-16 Telem ON" +#define TR_BINDING_CH9_16_TELEM_OFF "Ch9-16 Telem OFF" +#define TR_BINDING_25MW_CH1_8_TELEM_OFF TR("25mW Ch1-8 Tel OFF", "25mW Ch1-8 Telem OFF") +#define TR_BINDING_25MW_CH1_8_TELEM_ON TR("25mW Ch1-8 Tel ON", "25mW Ch1-8 Telem ON") +#define TR_BINDING_500MW_CH1_8_TELEM_OFF TR("500mW Ch1-8 Tel OFF", "500mW Ch1-8 Telem OFF") +#define TR_BINDING_500MW_CH9_16_TELEM_OFF TR("500mW Ch9-16 Tel OFF", "500mW Ch9-16 Telem OFF") +#define TR_BINDING_OPTION "Set at bind" #define TR_PROTOCOL_INVALID TR("Prot. invalid", "Protocol invalid") #define TR_MODULE_STATUS TR(INDENT "Status", INDENT "Module Status") +#define TR_MODULE_SYNC TR(INDENT "Sync", INDENT "Module Sync") #define TR_MULTI_SERVOFREQ TR(INDENT "Servo rate", INDENT "Servo update rate") #define TR_SYNCMENU "[Synch]" #define TR_LIMIT INDENT "Limit" @@ -904,6 +929,8 @@ #define TR_ALARMSWARN "ALARM" #define TR_SWITCHWARN TR("Przełą","Kontrola") #define TR_FAILSAFEWARN "FAILSAFE" +#define TR_NIGHTLY_WARNING TR("NIGHTLY", "NIGHTLY BUILD") +#define TR_NIGHTLY_NOTSAFE "Version not safe to fly" #define TR_WRONG_SDCARDVERSION TR("Expected ver: ","Expected version: ") #define TR_WRONG_PCBREV "Wrong PCB detected" #define TR_EMERGENCY_MODE "EMERGENCY MODE" @@ -950,7 +977,14 @@ #define TR_FORMATTING "Formatowanie.." #define TR_TEMP_CALIB "Temp. kalibracji" #define TR_TIME "Czas" +#define TR_MAXBAUDRATE "Max bauds" + +#define TR_BLUETOOTH "Bluetooth" #define TR_BAUDRATE "Prędkość BT" +#define LEN_BLUETOOTH_MODES "\011" +#define TR_BLUETOOTH_MODES "---\0 ""Telemetry""Trainer\0" + + #define TR_SD_INFO_TITLE "SD INFO" #define TR_SD_TYPE "Typ:" #define TR_SD_SPEED "Prędkość:" @@ -984,6 +1018,7 @@ #define TR_MENUSENSOR "CZUJNIK" #define TR_SENSOR "SENSOR" #define TR_COUNTRYCODE "Kod regionu" +#define TR_USBMODE "USB Mode" #define TR_VOICELANG "Język głosu" #define TR_UNITSSYSTEM "Jednostki" #define TR_EDIT "Edytuj" @@ -1001,7 +1036,10 @@ #define TR_RESET_TELEMETRY "Wyczyść telemetrię" #define TR_STATISTICS "Statystyki" #define TR_ABOUT_US "O nas" -#define TR_SETUP_SCREENS "Setup screens" +#define TR_USB_JOYSTICK "USB Joystick (HID)" +#define TR_USB_MASS_STORAGE "USB Storage (SD)" +#define TR_USB_SERIAL "USB Serial (Debug)" +#define TR_SETUP_SCREENS "Setup screens" #define TR_MONITOR_SCREENS "Monitors" #define TR_AND_SWITCH "Przełącznik AND" #define TR_SF "FS" @@ -1029,6 +1067,9 @@ #define TR_ANTENNACONFIRM2 "Make sure antenna is installed!" #define TR_LOWALARM INDENT "Alarm niski" #define TR_CRITICALALARM INDENT "Alarm krytyczny" +#define TR_RSSIALARM_WARN TR("RSSI","TELEMETRY RSSI") +#define TR_NO_RSSIALARM TR(INDENT "Alarms disabled", INDENT "Telemetry alarms disabled") +#define TR_DISABLE_ALARM TR(INDENT "Disable alarms", INDENT "Disable telemetry alarms") #define TR_ENABLE_POPUP "Aktywuj Popup" #define TR_DISABLE_POPUP "Wyłącz Popup" #define TR_POPUP "Popup" diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/translations/pt.h.txt opentx-companion22-2.2.1~ppa01~xenial/radio/src/translations/pt.h.txt --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/translations/pt.h.txt 2017-05-31 19:49:19.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/translations/pt.h.txt 2017-12-17 16:22:27.000000000 +0000 @@ -94,8 +94,11 @@ #define LEN_COUNTRYCODES TR("\002", "\007") #define TR_COUNTRYCODES TR("US""JP""EU", "America""Japan\0 ""Europe\0") +#define LEN_USBMODES TR("\006", "\010") +#define TR_USBMODES TR("Ask\0 ""Joyst\0""SDCard""Serial", "Ask\0 ""Joystick""Storage\0""Serial\0 ") + #define LEN_TARANIS_PROTOCOLS "\004" -#define TR_TARANIS_PROTOCOLS "OFF\0""PPM\0""XJT\0""DSM2""CRSF""MULT" +#define TR_TARANIS_PROTOCOLS "OFF\0""PPM\0""XJT\0""DSM2""CRSF""MULT""R9M\0""SBUS" #define LEN_TELEMETRY_PROTOCOLS "\017" #define TR_TELEMETRY_PROTOCOLS "FrSky S.PORT\0 ""FrSky D\0 ""FrSky D (cable)""TBS Crossfire\0 ""Spektrum\0 ""AFHDS2A IBUS\0 ""Multi Telemetry" @@ -107,7 +110,7 @@ #define TR_DSM_PROTOCOLS "LP45""DSM2""DSMX" #define LEN_MULTI_PROTOCOLS "\006" -#define TR_MULTI_PROTOCOLS "FlySky""Hubsan""FrSky\0""Hisky\0""V2x2\0 ""DSM\0 ""Devo\0 ""YD717\0""KN\0 ""SymaX\0""SLT\0 ""CX10\0 ""CG023\0""Bayang""ESky\0 ""MT99XX""MJXQ\0 ""Shenqi""FY326\0""SFHSS\0""J6 PRO""FQ777\0""Assan\0""Hontai""OLRS\0 ""FS 2A\0""Q2x2\0 ""Walk.\0""Q303\0 ""GW008\0""DM002\0" +#define TR_MULTI_PROTOCOLS "FlySky""Hubsan""FrSky\0""Hisky\0""V2x2\0 ""DSM\0 ""Devo\0 ""YD717\0""KN\0 ""SymaX\0""SLT\0 ""CX10\0 ""CG023\0""Bayang""ESky\0 ""MT99XX""MJXQ\0 ""Shenqi""FY326\0""SFHSS\0""J6 PRO""FQ777\0""Assan\0""Hontai""OLRS\0 ""FS 2A\0""Q2x2\0 ""Walk.\0""Q303\0 ""GW008\0""DM002\0""Cabell""Esky15""H8 3D\0" #define TR_MULTI_CUSTOM "Custom" @@ -430,7 +433,14 @@ #define LEN2_VTEMPLATES 13 #define LEN_VTEMPLATES "\015" -#define TR_VTEMPLATES "Tirar Mixagem""4CH Simples\0 ""Anular Motor\0""V-Tail\0 ""Elevon\\Zagi\0 ""eCCPM\0 ""Mixagem Heli\0""Testar Servos" +#define TR_TEMPLATE_CLEAR_MIXES "Tirar Mixagem" +#define TR_TEMPLATE_SIMPLE_4CH "4CH Simples\0 " +#define TR_TEMPLATE_STICKY_TCUT "Anular Motor\0" +#define TR_TEMPLATE_VTAIL "V-Tail\0 " +#define TR_TEMPLATE_DELTA "Elevon\\Zagi\0 " +#define TR_TEMPLATE_ECCPM "eCCPM\0 " +#define TR_TEMPLATE_HELI "Mixagem Heli\0" +#define TR_TEMPLATE_SERVO_TEST "Testar Servos" #define LEN_VSWASHTYPE "\004" #define TR_VSWASHTYPE "--- ""120 ""120X""140 ""90\0" @@ -541,7 +551,8 @@ #define TR_VTRAINER_SLAVE_JACK "Slave/Jack\0 " #define TR_VTRAINER_MASTER_SBUS_MODULE "Master/SBUS Module" #define TR_VTRAINER_MASTER_CPPM_MODULE "Master/CPPM Module" -#define TR_VTRAINER_MASTER_BATTERY "Master/Battery\0" +#define TR_VTRAINER_MASTER_BATTERY "Master/Battery\0 " +#define TR_VTRAINER_BLUETOOTH TR("Master/BT\0 ""Slave/BT\0", "Master/Bluetooth\0 ""Slave/Bluetooth\0 ") #define LEN_VFAILSAFE "\011" #define TR_VFAILSAFE "Not set\0 ""Hold\0 ""Custom\0 ""No pulses""Receiver\0" @@ -571,9 +582,17 @@ #define TR_VANTENNATYPES "Internal""Ext+Int\0" // ZERO TERMINATED STRINGS -#define INDENT "\001" -#define LEN_INDENT 1 -#define INDENT_WIDTH (FW/2) +#if defined(COLORLCD) + #define INDENT " " + #define LEN_INDENT 3 + #define INDENT_WIDTH 12 + #define BREAKSPACE "\036" +#else + #define INDENT "\001" + #define LEN_INDENT 1 + #define INDENT_WIDTH (FW/2) + #define BREAKSPACE " " +#endif #if defined(PCBTARANIS) #define TR_ENTER "[ENTER]" @@ -625,6 +644,8 @@ #endif #define TR_PROTO INDENT"Proto" #define TR_PPMFRAME "PPM frame" +#define TR_REFRESHRATE TR(INDENT "Refresh", INDENT "Refresh rate") +#define STR_WARN_BATTVOLTAGE TR(INDENT "Output is VBAT: ", INDENT "Warning: output level is VBAT: ") #define TR_MS "ms" #define TR_SWITCH "Chave" #define TR_TRIMS "Trims" @@ -687,6 +708,9 @@ #define TR_INACTIVITYALARM INDENT"Inactividade" #define TR_MEMORYWARNING INDENT"Memoria Baixa" #define TR_ALARMWARNING INDENT"Som Off" +#define TR_RSSISHUTDOWNALARM TR(INDENT "Rssi Shutdown", INDENT "Check Rssi on Shutdown") +#define TR_MODEL_STILL_POWERED "Model still powered" +#define TR_PRESS_ENTER_TO_CONFIRM "Press enter to confirm" #define TR_RENAVIG "RotEnc Navig" #define TR_THROTTLE_LABEL "Throttle" #define TR_THROTTLEREVERSE TR("Inverte Acel.", INDENT "Inverte Acel.") @@ -818,17 +842,25 @@ #define TR_MULTI_AUTOBIND TR(INDENT "Autobind",INDENT "Bind on powerup") #define TR_MULTI_DSM_AUTODTECT TR(INDENT "Autodetect", INDENT "Autodetect format") #define TR_MULTI_LOWPOWER TR(INDENT "Low power", INDENT "Low power mode") +#define TR_MODULE_TELEMETRY TR(INDENT "Mod telem.", INDENT "Module telemetry") #define TR_DISABLE_INTERNAL TR("Disable int. RF", "Disable internal RF") #define TR_MODULE_NO_SERIAL_MODE TR("!serial mode", "Not in serial mode") #define TR_MODULE_NO_INPUT TR("No input", "No serial input") #define TR_MODULE_NO_TELEMETRY TR3( "No telmetry", "No MULTI_TELEMETRY", "No telemetry (enable MULTI_TELEMETRY)") +#define TR_MODULE_WAITFORBIND "Bind to load protocol" #define TR_MODULE_BINDING "Binding" -#define TR_BINDING_MODE1 "Ch1-8 Telem ON" -#define TR_BINDING_MODE2 "Ch1-8 Telem OFF" -#define TR_BINDING_MODE3 "Ch9-16 Telem ON" -#define TR_BINDING_MODE4 "Ch9-16 Telem OFF" +#define TR_BINDING_CH1_8_TELEM_ON "Ch1-8 Telem ON" +#define TR_BINDING_CH1_8_TELEM_OFF "Ch1-8 Telem OFF" +#define TR_BINDING_CH9_16_TELEM_ON "Ch9-16 Telem ON" +#define TR_BINDING_CH9_16_TELEM_OFF "Ch9-16 Telem OFF" +#define TR_BINDING_25MW_CH1_8_TELEM_OFF TR("25mW Ch1-8 Tel OFF", "25mW Ch1-8 Telem OFF") +#define TR_BINDING_25MW_CH1_8_TELEM_ON TR("25mW Ch1-8 Tel ON", "25mW Ch1-8 Telem ON") +#define TR_BINDING_500MW_CH1_8_TELEM_OFF TR("500mW Ch1-8 Tel OFF", "500mW Ch1-8 Telem OFF") +#define TR_BINDING_500MW_CH9_16_TELEM_OFF TR("500mW Ch9-16 Tel OFF", "500mW Ch9-16 Telem OFF") +#define TR_BINDING_OPTION "Set at bind" #define TR_PROTOCOL_INVALID TR("Prot. invalid", "Protocol invalid") #define TR_MODULE_STATUS TR(INDENT "Status", INDENT "Module Status") +#define TR_MODULE_SYNC TR(INDENT "Sync", INDENT "Module Sync") #define TR_MULTI_SERVOFREQ TR(INDENT "Servo rate", INDENT "Servo update rate") #define TR_LIMIT INDENT"Limite" #define TR_MINRSSI "Min Rssi" @@ -871,6 +903,8 @@ #define TR_ALARMSWARN "ALARMES" #define TR_SWITCHWARN "CHAVES" #define TR_FAILSAFEWARN "FAILSAFE" +#define TR_NIGHTLY_WARNING TR("NIGHTLY", "NIGHTLY BUILD") +#define TR_NIGHTLY_NOTSAFE "Version not safe to fly" #define TR_WRONG_SDCARDVERSION TR("Expected ver: ","Expected version: ") #define TR_WRONG_PCBREV "Wrong PCB detected" #define TR_EMERGENCY_MODE "EMERGENCY MODE" @@ -917,7 +951,13 @@ #define TR_FORMATTING "Formatando..." #define TR_TEMP_CALIB "Temp. Calib" #define TR_TIME "Time" +#define TR_MAXBAUDRATE "Max bauds" + +#define TR_BLUETOOTH "Bluetooth" #define TR_BAUDRATE "BT Baudrate" +#define LEN_BLUETOOTH_MODES "\011" +#define TR_BLUETOOTH_MODES "---\0 ""Telemetry""Trainer\0" + #define TR_SD_INFO_TITLE "SD INFO" #define TR_SD_TYPE "Tipe" #define TR_SD_SPEED "Velocidade" @@ -951,6 +991,7 @@ #define TR_MENUSENSOR "SENSOR" #define TR_SENSOR "SENSOR" #define TR_COUNTRYCODE "Country Code" +#define TR_USBMODE "USB Mode" #define TR_VOICELANG "Voice Language" #define TR_UNITSSYSTEM "Units" #define TR_EDIT "Edit" @@ -968,7 +1009,10 @@ #define TR_RESET_TELEMETRY "Reset Telemetry" #define TR_STATISTICS "Statistics" #define TR_ABOUT_US "About Us" -#define TR_SETUP_SCREENS "Setup screens" +#define TR_USB_JOYSTICK "USB Joystick (HID)" +#define TR_USB_MASS_STORAGE "USB Storage (SD)" +#define TR_USB_SERIAL "USB Serial (Debug)" +#define TR_SETUP_SCREENS "Setup screens" #define TR_MONITOR_SCREENS "Monitors" #define TR_AND_SWITCH "AND Switch" #define TR_SF "CF" @@ -982,7 +1026,7 @@ #define TR_SET "[Set]" #define TR_TRAINER "Trainer" #define TR_ANTENNAPROBLEM CENTER "TX Antenna problem!" -#define TR_MODELIDUSED TR("ID already used","Model ID already used") +#define TR_MODELIDUSED TR("ID used in:", "Receiver ID used in:") #define TR_MODULE INDENT "Module" #define TR_TELEMETRY_TYPE TR("Type", "Telemetry Type") #define TR_TELEMETRY_SENSORS "Sensors" @@ -996,6 +1040,9 @@ #define TR_ANTENNACONFIRM2 "Make sure antenna is installed!" #define TR_LOWALARM INDENT "Low Alarm" #define TR_CRITICALALARM INDENT "Critical Alarm" +#define TR_RSSIALARM_WARN TR("RSSI","TELEMETRY RSSI") +#define TR_NO_RSSIALARM TR(INDENT "Alarms disabled", INDENT "Telemetry alarms disabled") +#define TR_DISABLE_ALARM TR(INDENT "Disable alarms", INDENT "Disable telemetry alarms") #define TR_ENABLE_POPUP "Enable Popup" #define TR_DISABLE_POPUP "Disable Popup" #define TR_POPUP "Popup" diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/translations/se.h.txt opentx-companion22-2.2.1~ppa01~xenial/radio/src/translations/se.h.txt --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/translations/se.h.txt 2017-05-31 19:49:19.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/translations/se.h.txt 2017-12-17 16:22:27.000000000 +0000 @@ -94,8 +94,11 @@ #define LEN_COUNTRYCODES TR("\002", "\007") #define TR_COUNTRYCODES TR("US""JP""EU", "Amerika""Japan\0 ""Europa\0") +#define LEN_USBMODES TR("\006", "\010") +#define TR_USBMODES TR("Ask\0 ""Joyst\0""SDCard""Serial", "Ask\0 ""Joystick""Storage\0""Serial\0 ") + #define LEN_TARANIS_PROTOCOLS "\004" -#define TR_TARANIS_PROTOCOLS "Av\0 ""PPM\0""XJT\0""DSM2""CRSF""MULT" +#define TR_TARANIS_PROTOCOLS "Av\0 ""PPM\0""XJT\0""DSM2""CRSF""MULT""R9M\0""SBUS" #define LEN_TELEMETRY_PROTOCOLS "\017" #define TR_TELEMETRY_PROTOCOLS "FrSky S.PORT\0 ""FrSky D\0 ""FrSky D (cable)""TBS Crossfire\0 ""Spektrum\0 ""AFHDS2A IBUS\0 ""Multi Telemetry" @@ -107,7 +110,7 @@ #define TR_DSM_PROTOCOLS "LP45""DSM2""DSMX" #define LEN_MULTI_PROTOCOLS "\006" -#define TR_MULTI_PROTOCOLS "FlySky""Hubsan""FrSky\0""Hisky\0""V2x2\0 ""DSM\0 ""Devo\0 ""YD717\0""KN\0 ""SymaX\0""SLT\0 ""CX10\0 ""CG023\0""Bayang""ESky\0 ""MT99XX""MJXQ\0 ""Shenqi""FY326\0""SFHSS\0""J6 PRO""FQ777\0""Assan\0""Hontai""OLRS\0 ""FS 2A\0""Q2x2\0 ""Walk.\0""Q303\0 ""GW008\0""DM002\0" +#define TR_MULTI_PROTOCOLS "FlySky""Hubsan""FrSky\0""Hisky\0""V2x2\0 ""DSM\0 ""Devo\0 ""YD717\0""KN\0 ""SymaX\0""SLT\0 ""CX10\0 ""CG023\0""Bayang""ESky\0 ""MT99XX""MJXQ\0 ""Shenqi""FY326\0""SFHSS\0""J6 PRO""FQ777\0""Assan\0""Hontai""OLRS\0 ""FS 2A\0""Q2x2\0 ""Walk.\0""Q303\0 ""GW008\0""DM002\0""Cabell""Esky15""H8 3D\0" #define TR_MULTI_CUSTOM "Custom" @@ -436,9 +439,16 @@ #define LEN_GPSFORMAT "\004" #define TR_GPSFORMAT "HMS NMEA" -#define LEN2_VTEMPLATES 13 -#define LEN_VTEMPLATES "\015" -#define TR_VTEMPLATES "Nolla Mixar\0\0""Enkel 4kanal\0""Gasklippning\0""V-Stjärt \0""Deltavinge \0""eCCPM \0""Helikopter \0""Servotest \0" +#define LEN2_VTEMPLATES 12 +#define LEN_VTEMPLATES "\014" +#define TR_TEMPLATE_CLEAR_MIXES "Nolla Mixar\0" +#define TR_TEMPLATE_SIMPLE_4CH "Enkel 4kanal" +#define TR_TEMPLATE_STICKY_TCUT "Gasklippning" +#define TR_TEMPLATE_VTAIL "V-Stjärt " +#define TR_TEMPLATE_DELTA "Deltavinge " +#define TR_TEMPLATE_ECCPM "eCCPM " +#define TR_TEMPLATE_HELI "Helikopter " +#define TR_TEMPLATE_SERVO_TEST "Servotest " #define LEN_VSWASHTYPE "\004" #define TR_VSWASHTYPE "--- ""120 ""120X""140 ""90\0 " @@ -562,10 +572,11 @@ #define TR_VTRAINER_SLAVE_JACK "Elev./Uttag\0 " #define TR_VTRAINER_MASTER_SBUS_MODULE "Lärare/SBUS-Modul\0" #define TR_VTRAINER_MASTER_CPPM_MODULE "Lärare/CPPM-Modul\0" -#define TR_VTRAINER_MASTER_BATTERY "Lärare/Batteri\0" +#define TR_VTRAINER_MASTER_BATTERY "Lärare/Batteri\0 " +#define TR_VTRAINER_BLUETOOTH TR("Master/BT\0 ""Slave/BT\0", "Master/Bluetooth\0 ""Slave/Bluetooth\0 ") #define LEN_VFAILSAFE "\011" -#define TR_VFAILSAFE "Ej givet""Lås Servo""Anpassat\0""Pulsfritt""Mottagare" +#define TR_VFAILSAFE "Ej givet\0""Lås Servo""Anpassat\0""Pulsfritt""Mottagare" #if defined(TELEMETRY_MAVLINK) #define LEN_MAVLINK_BAUDS "\006" @@ -657,6 +668,8 @@ #define TR_PROTO TR(INDENT "Proto", INDENT "Protokoll") #if defined(CPUARM) #define TR_PPMFRAME INDENT "PPM-paket" +#define TR_REFRESHRATE TR(INDENT "Refresh", INDENT "Refresh rate") +#define STR_WARN_BATTVOLTAGE TR(INDENT "Output is VBAT: ", INDENT "Warning: output level is VBAT: ") #else #define TR_PPMFRAME "PPM-paket" #endif @@ -722,6 +735,9 @@ #define TR_INACTIVITYALARM INDENT"Inaktivitet" #define TR_MEMORYWARNING INDENT"Lite Minne" #define TR_ALARMWARNING INDENT"Ljud Av" +#define TR_RSSISHUTDOWNALARM TR(INDENT "Rssi Shutdown", INDENT "Check Rssi on Shutdown") +#define TR_MODEL_STILL_POWERED "Model still powered" +#define TR_PRESS_ENTER_TO_CONFIRM "Press enter to confirm" #define TR_RENAVIG "RotEnk Navig" #define TR_THROTTLE_LABEL "Gas" #define TR_THROTTLEREVERSE TR("Inv.Gas", INDENT "Inverterad Gas") @@ -863,17 +879,25 @@ #define TR_MULTI_AUTOBIND TR(INDENT "Autobind",INDENT "Bind on powerup") #define TR_MULTI_DSM_AUTODTECT TR(INDENT "Autodetect", INDENT "Autodetect format") #define TR_MULTI_LOWPOWER TR(INDENT "Low power", INDENT "Low power mode") +#define TR_MODULE_TELEMETRY TR(INDENT "Mod telem.", INDENT "Module telemetry") #define TR_DISABLE_INTERNAL TR("Disable int. RF", "Disable internal RF") #define TR_MODULE_NO_SERIAL_MODE TR("!serial mode", "Not in serial mode") #define TR_MODULE_NO_INPUT TR("No input", "No serial input") #define TR_MODULE_NO_TELEMETRY TR3( "No telmetry", "No MULTI_TELEMETRY", "No telemetry (enable MULTI_TELEMETRY)") +#define TR_MODULE_WAITFORBIND "Bind to load protocol" #define TR_MODULE_BINDING "Binding" -#define TR_BINDING_MODE1 "Ch1-8 Telem ON" -#define TR_BINDING_MODE2 "Ch1-8 Telem OFF" -#define TR_BINDING_MODE3 "Ch9-16 Telem ON" -#define TR_BINDING_MODE4 "Ch9-16 Telem OFF" +#define TR_BINDING_CH1_8_TELEM_ON "Ch1-8 Telem ON" +#define TR_BINDING_CH1_8_TELEM_OFF "Ch1-8 Telem OFF" +#define TR_BINDING_CH9_16_TELEM_ON "Ch9-16 Telem ON" +#define TR_BINDING_CH9_16_TELEM_OFF "Ch9-16 Telem OFF" +#define TR_BINDING_25MW_CH1_8_TELEM_OFF TR("25mW Ch1-8 Tel OFF", "25mW Ch1-8 Telem OFF") +#define TR_BINDING_25MW_CH1_8_TELEM_ON TR("25mW Ch1-8 Tel ON", "25mW Ch1-8 Telem ON") +#define TR_BINDING_500MW_CH1_8_TELEM_OFF TR("500mW Ch1-8 Tel OFF", "500mW Ch1-8 Telem OFF") +#define TR_BINDING_500MW_CH9_16_TELEM_OFF TR("500mW Ch9-16 Tel OFF", "500mW Ch9-16 Telem OFF") +#define TR_BINDING_OPTION "Set at bind" #define TR_PROTOCOL_INVALID TR("Prot. invalid", "Protocol invalid") #define TR_MODULE_STATUS TR(INDENT "Status", INDENT "Module Status") +#define TR_MODULE_SYNC TR(INDENT "Sync", INDENT "Module Sync") #define TR_MULTI_SERVOFREQ TR(INDENT "Servo rate", INDENT "Servo update rate") #define TR_LIMIT INDENT "Nivå" #define TR_MINRSSI "Min Rssi" @@ -916,6 +940,8 @@ #define TR_ALARMSWARN "ALARM" #define TR_SWITCHWARN "BRYTARE" #define TR_FAILSAFEWARN "FAILSAFE" +#define TR_NIGHTLY_WARNING TR("NIGHTLY", "NIGHTLY BUILD") +#define TR_NIGHTLY_NOTSAFE "Version not safe to fly" #define TR_SDCARDVERSIONWARN "SD Card Check" #define TR_WRONG_SDCARDVERSION TR("Expected ver: ","Expected version: ") #define TR_WRONG_PCBREV "Wrong PCB detected" @@ -963,7 +989,13 @@ #define TR_FORMATTING "Formaterar..." #define TR_TEMP_CALIB "Temp. kalib." #define TR_TIME "Tid " +#define TR_MAXBAUDRATE "Max bauds" + +#define TR_BLUETOOTH "Bluetooth" #define TR_BAUDRATE "BT Baudrate" +#define LEN_BLUETOOTH_MODES "\011" +#define TR_BLUETOOTH_MODES "---\0 ""Telemetry""Trainer\0" + #define TR_SD_INFO_TITLE "SD INFO" #define TR_SD_TYPE "Typ: " #define TR_SD_SPEED "Hastighet:" @@ -997,6 +1029,7 @@ #define TR_MENUSENSOR "SENSOR" #define TR_SENSOR "SENSOR" #define TR_COUNTRYCODE "Landskod" +#define TR_USBMODE "USB Mode" #define TR_VOICELANG "Röstspråk" #define TR_UNITSSYSTEM "Enheter" #define TR_EDIT "Redigera" @@ -1014,7 +1047,10 @@ #define TR_RESET_TELEMETRY "Nollställ Telemetri" #define TR_STATISTICS "Statistik" #define TR_ABOUT_US "Om Oss" -#define TR_SETUP_SCREENS "Setup screens" +#define TR_USB_JOYSTICK "USB Joystick (HID)" +#define TR_USB_MASS_STORAGE "USB Storage (SD)" +#define TR_USB_SERIAL "USB Serial (Debug)" +#define TR_SETUP_SCREENS "Setup screens" #define TR_MONITOR_SCREENS "Monitors" #define TR_AND_SWITCH "OCH Brytare" #define TR_SF "BF" @@ -1042,6 +1078,9 @@ #define TR_ANTENNACONFIRM2 "Make sure antenna is installed!" #define TR_LOWALARM INDENT "Låg-alarm" #define TR_CRITICALALARM INDENT "Kritiskt alarm" +#define TR_RSSIALARM_WARN TR("RSSI","TELEMETRY RSSI") +#define TR_NO_RSSIALARM TR(INDENT "Alarms disabled", INDENT "Telemetry alarms disabled") +#define TR_DISABLE_ALARM TR(INDENT "Disable alarms", INDENT "Disable telemetry alarms") #define TR_ENABLE_POPUP "Slå på Dialog" #define TR_DISABLE_POPUP "Slå av Dialog" #define TR_POPUP "Popup" diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/translations/tts_ru.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/translations/tts_ru.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/translations/tts_ru.cpp 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/translations/tts_ru.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -0,0 +1,222 @@ +/* + * Author + * - Alexander Novikov (mr.pokryshkin@gmail.com) + * + * tts_ru is based on tts_de and tts_en + * + * opentx is based on code named + * gruvin9x by Bryan J. Rentoul: http://code.google.com/p/gruvin9x/, + * er9x by Erez Raviv: http://code.google.com/p/er9x/, + * and the original (and ongoing) project by + * Thomas Husterer, th9x: http://code.google.com/p/th9x/ + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + * + * 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. + * + */ + +#include "opentx.h" + +enum RusPrompts { + RU_PROMPT_NUMBERS_BASE = 0, + RU_PROMPT_ZERO = RU_PROMPT_NUMBERS_BASE+0, //02-99 + RU_PROMPT_HUNDRED = RU_PROMPT_NUMBERS_BASE+100, //100,200 .. 900 + + RU_PROMPT_AND = RU_PROMPT_NUMBERS_BASE+110, // и + RU_PROMPT_MINUS = RU_PROMPT_NUMBERS_BASE+111, // минус + RU_PROMPT_UNITS_BASE = RU_PROMPT_NUMBERS_BASE + 113, + RU_PROMPT_POINT_BASE = RU_PROMPT_NUMBERS_BASE + 165, //.0 - .9 + RU_PROMPT_FEMALE_ONE = RU_PROMPT_NUMBERS_BASE + 180, + RU_PROMPT_FEMALE_TWO = RU_PROMPT_NUMBERS_BASE + 190, + + RU_PROMPT_THOUSAND1 = RU_PROMPT_NUMBERS_BASE+200, //1000 + RU_PROMPT_THOUSAND2 = RU_PROMPT_NUMBERS_BASE+201, //2000 + RU_PROMPT_THOUSAND5 = RU_PROMPT_NUMBERS_BASE+202, //5000 +}; +#define MALE 0x00 +#define FEMALE 0x01 +#define RU_FEMALE_UNIT 0xFF + +#if defined(VOICE) + +#if defined(CPUARM) + #define RU_PUSH_UNIT_PROMPT(u, p) ru_pushUnitPrompt((u), (p), id) +#else + #define RU_PUSH_UNIT_PROMPT(u, p) pushUnitPrompt((u), (p)) +#endif + +I18N_PLAY_FUNCTION(ru, pushUnitPrompt, uint8_t unitprompt, int16_t number) +{ +#if defined(CPUARM) + if (number < 0){ // if negative number, we have to use 2 units form (for example value = 1.3) + PUSH_UNIT_PROMPT(unitprompt, 2); + } + else{ + int16_t mod10 = number % 10; + if (number == 0) + PUSH_UNIT_PROMPT(unitprompt, 0); + else if (number == 1) + PUSH_UNIT_PROMPT(unitprompt, 1); + else if (number>=2 && number <=4) + PUSH_UNIT_PROMPT(unitprompt, 2); + else if (number>=5 && number <=20) + PUSH_UNIT_PROMPT(unitprompt, 5); + else if (mod10 == 1) + PUSH_UNIT_PROMPT(unitprompt, 1); + else if (mod10 >= 2 && mod10 <=4) + PUSH_UNIT_PROMPT(unitprompt, 2); + else + PUSH_UNIT_PROMPT(unitprompt, 5); + } +#else + + // TODO: add rules for Russian language + unitprompt = RU_PROMPT_UNITS_BASE + unitprompt*4; + if (number == 1) + PUSH_NUMBER_PROMPT(unitprompt); + else + PUSH_NUMBER_PROMPT(unitprompt+1); +#endif +} + +I18N_PLAY_FUNCTION(ru, playNumber, getvalue_t number, uint8_t unit, uint8_t att) +{ + if (number < 0) { + PUSH_NUMBER_PROMPT(RU_PROMPT_MINUS); + number = -number; + } + +#if !defined(CPUARM) + if (unit) { + unit--; + convertUnit(number, unit); + if (IS_IMPERIAL_ENABLE()) { + if (unit == UNIT_DIST) { + unit = UNIT_FEET; + } + if (unit == UNIT_SPEED) { + unit = UNIT_KTS; + } + } + unit++; + } +#endif + div_t qr = div((int)number, 10); + int8_t mode = MODE(att); + if (mode > 0 && att != RU_FEMALE_UNIT) { +#if defined(CPUARM) + if (mode == 2) { + number /= 10; + } +#else + // we assume that we are PREC1 +#endif + if (qr.rem) { + PLAY_NUMBER(qr.quot, 0, 0); + PUSH_NUMBER_PROMPT(RU_PROMPT_POINT_BASE + qr.rem); + number = -1; + } + else { + number = qr.quot; + } + } + + int16_t tmp = number; + + if (number >= 1000) { + PLAY_NUMBER(number / 1000, RU_FEMALE_UNIT, 0); // female + uint8_t thousands = number / 1000; + int16_t mod10 = thousands % 10; + if (thousands == 1) + PUSH_NUMBER_PROMPT(RU_PROMPT_THOUSAND1); + else if (thousands>=2 && thousands <=4) + PUSH_NUMBER_PROMPT(RU_PROMPT_THOUSAND2); + else if (thousands>=5 && thousands <=20) + PUSH_NUMBER_PROMPT(RU_PROMPT_THOUSAND5); + else if (mod10 == 1) + PUSH_NUMBER_PROMPT(RU_PROMPT_THOUSAND1); + else if (mod10 >= 2 && mod10 <=4) + PUSH_NUMBER_PROMPT(RU_PROMPT_THOUSAND2); + else + PUSH_NUMBER_PROMPT(RU_PROMPT_THOUSAND5); + number %= 1000; + if (number == 0) + number = -1; + } + if (number >= 100) { + PUSH_NUMBER_PROMPT(RU_PROMPT_HUNDRED + (number/100)-1); + number %= 100; + if (number == 0) + number = -1; + } + if (number >= 0) { + uint8_t attr = MALE; + switch(unit) { + case RU_FEMALE_UNIT: + case UNIT_MPH: + case UNIT_FLOZ: + case UNIT_MINUTES: + case UNIT_SECONDS: + attr = FEMALE; + break; + default: + attr = MALE; + break; + } + uint8_t lastDigit = number % 10; + uint8_t ten=(number - (number % 10))/10; + if (lastDigit == 1 && number != 11 && attr == FEMALE) + PUSH_NUMBER_PROMPT(RU_PROMPT_FEMALE_ONE + ten); + else if (lastDigit == 2 && number !=12 && attr == FEMALE) + PUSH_NUMBER_PROMPT(RU_PROMPT_FEMALE_TWO + ten); + else + PUSH_NUMBER_PROMPT(RU_PROMPT_ZERO + number); + } + + if (unit) { + if (mode > 0 && qr.rem) // number with decimal point + RU_PUSH_UNIT_PROMPT(unit, -1); // force 2 units form, if float value + else + RU_PUSH_UNIT_PROMPT(unit, tmp); + } +} + +I18N_PLAY_FUNCTION(ru, playDuration, int seconds PLAY_DURATION_ATT) +{ + if (seconds == 0) { + PLAY_NUMBER(seconds, 0, 0); + return; + } + + if (seconds < 0) { + PUSH_NUMBER_PROMPT(RU_PROMPT_MINUS); + seconds = -seconds; + } + + uint8_t tmp = seconds / 3600; + seconds %= 3600; + if (tmp > 0 || IS_PLAY_TIME()) { + PLAY_NUMBER(tmp, UNIT_HOURS, 0); + } + + tmp = seconds / 60; + seconds %= 60; + if (tmp > 0) { + PLAY_NUMBER(tmp, UNIT_MINUTES, 0); + if (seconds > 0) + PUSH_NUMBER_PROMPT(RU_PROMPT_AND); + } + if (seconds > 0) { + PLAY_NUMBER(seconds, UNIT_SECONDS, 0); + } +} + +LANGUAGE_PACK_DECLARE(ru, "Russian"); + +#endif diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/translations.cpp opentx-companion22-2.2.1~ppa01~xenial/radio/src/translations.cpp --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/translations.cpp 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/translations.cpp 2017-12-17 16:22:27.000000000 +0000 @@ -102,11 +102,15 @@ #endif #if defined(PXX) || defined(CPUARM) ISTR(COUNTRYCODES) + ISTR(USBMODES) ISTR(VFAILSAFE) #endif #if defined(CPUARM) ISTR(VTRAINERMODES) ISTR(TARANIS_PROTOCOLS) + ISTR(R9M_MODES) + ISTR(R9M_FCC_POWER_VALUES) + ISTR(R9M_LBT_POWER_VALUES) ISTR(TELEMETRY_PROTOCOLS) ISTR(XJT_PROTOCOLS) ISTR(DSM_PROTOCOLS) @@ -119,6 +123,9 @@ ISTR(VFORMULAS) ISTR(VPREC) ISTR(VCELLINDEX) +#if defined(BLUETOOTH) + ISTR(BLUETOOTH_MODES) +#endif ISTR(VANTENNATYPES) #endif #if defined(TELEMETRY_MAVLINK) @@ -157,6 +164,10 @@ #endif const pm_char STR_PROTO[] PROGMEM = TR_PROTO; const pm_char STR_PPMFRAME[] PROGMEM = TR_PPMFRAME; +#if defined(CPUARM) +const pm_char STR_REFRESHRATE[] PROGMEM = TR_REFRESHRATE; +const pm_char SSTR_WARN_BATTVOLTAGE[] PROGMEM = STR_WARN_BATTVOLTAGE; +#endif const pm_char STR_MS[] PROGMEM = TR_MS; const pm_char STR_SWITCH[] PROGMEM = TR_SWITCH; const pm_char STR_TRIMS[] PROGMEM = TR_TRIMS; @@ -230,6 +241,9 @@ const pm_char STR_INACTIVITYALARM[] PROGMEM = TR_INACTIVITYALARM; const pm_char STR_MEMORYWARNING[] PROGMEM = TR_MEMORYWARNING; const pm_char STR_ALARMWARNING[] PROGMEM = TR_ALARMWARNING; +const pm_char STR_RSSISHUTDOWNALARM[] PROGMEM = TR_RSSISHUTDOWNALARM; +const pm_char STR_MODEL_STILL_POWERED[] PROGMEM = TR_MODEL_STILL_POWERED; +const pm_char STR_PRESS_ENTER_TO_CONFIRM[] PROGMEM = TR_PRESS_ENTER_TO_CONFIRM; #if defined(ROTARY_ENCODERS) const pm_char STR_RENAVIG[] PROGMEM = TR_RENAVIG; #endif @@ -377,13 +391,16 @@ const pm_char STR_SYNCMENU[] PROGMEM = TR_SYNCMENU; const pm_char STR_INTERNALRF[] PROGMEM = TR_INTERNALRF; const pm_char STR_EXTERNALRF[] PROGMEM = TR_EXTERNALRF; +const pm_char STR_MODULE_TELEMETRY[] PROGMEM = TR_MODULE_TELEMETRY; const pm_char STR_COUNTRYCODE[] PROGMEM = TR_COUNTRYCODE; +const pm_char STR_USBMODE[] PROGMEM = TR_USBMODE; const pm_char STR_FAILSAFE[] PROGMEM = TR_FAILSAFE; const pm_char STR_FAILSAFESET[] PROGMEM = TR_FAILSAFESET; const pm_char STR_HOLD[] PROGMEM = TR_HOLD; const pm_char STR_NONE[] PROGMEM = TR_NONE; const pm_char STR_MENUSENSOR[] PROGMEM = TR_MENUSENSOR; const pm_char STR_SENSOR[] PROGMEM = TR_SENSOR; +const pm_char STR_DISABLE_INTERNAL[] PROGMEM = TR_DISABLE_INTERNAL; #endif const pm_char STR_INVERT_THR[] PROGMEM = TR_INVERT_THR; @@ -449,6 +466,9 @@ const pm_char STR_RESET_TELEMETRY[] PROGMEM = TR_RESET_TELEMETRY; const pm_char STR_STATISTICS[] PROGMEM = TR_STATISTICS; const pm_char STR_ABOUT_US[] PROGMEM = TR_ABOUT_US; +const pm_char STR_USB_JOYSTICK[] PROGMEM = TR_USB_JOYSTICK; +const pm_char STR_USB_MASS_STORAGE[] PROGMEM = TR_USB_MASS_STORAGE; +const pm_char STR_USB_SERIAL[] PROGMEM = TR_USB_SERIAL; const pm_char STR_SETUP_SCREENS[] PROGMEM = TR_SETUP_SCREENS; const pm_char STR_MONITOR_SCREENS[] PROGMEM = TR_MONITOR_SCREENS; #endif @@ -458,18 +478,18 @@ const pm_char STR_MULTI_RFTUNE[] PROGMEM = TR_MULTI_RFTUNE; const pm_char STR_MULTI_TELEMETRY[] PROGMEM = TR_MULTI_TELEMETRY; const pm_char STR_MULTI_VIDFREQ[] PROGMEM = TR_MULTI_VIDFREQ; -const pm_char STR_MULTI_RFPOWER[] PROGMEM = TR_MULTI_RFPOWER; const pm_char STR_MULTI_OPTION[] PROGMEM = TR_MULTI_OPTION; const pm_char STR_MULTI_AUTOBIND[] PROGMEM = TR_MULTI_AUTOBIND; const pm_char STR_MULTI_DSM_AUTODTECT[] PROGMEM = TR_MULTI_DSM_AUTODTECT; const pm_char STR_MULTI_LOWPOWER[] PROGMEM = TR_MULTI_LOWPOWER; -const pm_char STR_DISABLE_INTERNAL[] PROGMEM = TR_DISABLE_INTERNAL; const pm_char STR_MODULE_NO_SERIAL_MODE[] PROGMEM = TR_MODULE_NO_SERIAL_MODE; const pm_char STR_MODULE_NO_INPUT[] PROGMEM = TR_MODULE_NO_INPUT; +const pm_char STR_MODULE_WAITFORBIND[] PROGMEM = TR_MODULE_WAITFORBIND; const pm_char STR_MODULE_NO_TELEMETRY[] PROGMEM = TR_MODULE_NO_TELEMETRY; const pm_char STR_MODULE_BINDING[] PROGMEM = TR_MODULE_BINDING; const pm_char STR_PROTOCOL_INVALID[] PROGMEM = TR_PROTOCOL_INVALID; const pm_char STR_MODULE_STATUS[] PROGMEM = TR_MODULE_STATUS; +const pm_char STR_MODULE_SYNC[] PROGMEM = TR_MODULE_SYNC; const pm_char STR_MULTI_SERVOFREQ[] PROGMEM = TR_MULTI_SERVOFREQ; #if LCD_W < 212 const pm_char STR_SUBTYPE[] PROGMEM = TR_SUBTYPE; @@ -498,6 +518,10 @@ const pm_char STR_ALARMSWARN[] PROGMEM = TR_ALARMSWARN; const pm_char STR_SWITCHWARN[] PROGMEM = TR_SWITCHWARN; const pm_char STR_FAILSAFEWARN[] PROGMEM = TR_FAILSAFEWARN; +#if defined(NIGHTLY_BUILD_WARNING) +const pm_char STR_NIGHTLY_WARNING[] PROGMEM = TR_NIGHTLY_WARNING; +const pm_char STR_NIGHTLY_NOTSAFE[] PROGMEM = TR_NIGHTLY_NOTSAFE; +#endif const pm_char STR_WRONG_SDCARDVERSION[] PROGMEM = TR_WRONG_SDCARDVERSION; const pm_char STR_WRONG_PCBREV[] PROGMEM = TR_WRONG_PCBREV; const pm_char STR_EMERGENCY_MODE[] PROGMEM = TR_EMERGENCY_MODE; @@ -544,6 +568,7 @@ const pm_char STR_FORMATTING[] PROGMEM = TR_FORMATTING; const pm_char STR_TEMP_CALIB[] PROGMEM = TR_TEMP_CALIB; const pm_char STR_TIME[] PROGMEM = TR_TIME; +const pm_char STR_MAXBAUDRATE[] PROGMEM = TR_MAXBAUDRATE; const pm_char STR_BAUDRATE[] PROGMEM = TR_BAUDRATE; const pm_char STR_SD_INFO_TITLE[] PROGMEM = TR_SD_INFO_TITLE; const pm_char STR_SD_TYPE[] PROGMEM = TR_SD_TYPE; @@ -592,10 +617,15 @@ #if defined(CPUARM) const pm_char STR_TRAINER[] PROGMEM = TR_TRAINER; const pm_char STR_MODULE_BIND[] PROGMEM = TR_MODULE_BIND; - const pm_char STR_BINDING_1_8_TELEM_ON[] PROGMEM = TR_BINDING_MODE1; - const pm_char STR_BINDING_1_8_TELEM_OFF[] PROGMEM = TR_BINDING_MODE2; - const pm_char STR_BINDING_9_16_TELEM_ON[] PROGMEM = TR_BINDING_MODE3; - const pm_char STR_BINDING_9_16_TELEM_OFF[] PROGMEM = TR_BINDING_MODE4; + const pm_char STR_BINDING_1_8_TELEM_ON[] PROGMEM = TR_BINDING_CH1_8_TELEM_ON; + const pm_char STR_BINDING_1_8_TELEM_OFF[] PROGMEM = TR_BINDING_CH1_8_TELEM_OFF; + const pm_char STR_BINDING_9_16_TELEM_ON[] PROGMEM = TR_BINDING_CH9_16_TELEM_ON; + const pm_char STR_BINDING_9_16_TELEM_OFF[] PROGMEM = TR_BINDING_CH9_16_TELEM_OFF; + const pm_char STR_BINDING_25MW_CH1_8_TELEM_OFF[] PROGMEM = TR_BINDING_25MW_CH1_8_TELEM_OFF; + const pm_char STR_BINDING_25MW_CH1_8_TELEM_ON[] PROGMEM = TR_BINDING_25MW_CH1_8_TELEM_ON; + const pm_char STR_BINDING_500MW_CH1_8_TELEM_OFF[] PROGMEM = TR_BINDING_500MW_CH1_8_TELEM_OFF; + const pm_char STR_BINDING_500MW_CH9_16_TELEM_OFF[] PROGMEM = TR_BINDING_500MW_CH9_16_TELEM_OFF; + const pm_char STR_BINDING_OPTION[] PROGMEM = TR_BINDING_OPTION; const pm_char STR_CHANNELRANGE[] PROGMEM = TR_CHANNELRANGE; const pm_char STR_ANTENNASELECTION[] PROGMEM = TR_ANTENNASELECTION; const pm_char STR_ANTENNACONFIRM1[] PROGMEM = TR_ANTENNACONFIRM1; @@ -604,10 +634,13 @@ const pm_char STR_PREFLIGHT[] PROGMEM = TR_PREFLIGHT; const pm_char STR_CHECKLIST[] PROGMEM = TR_CHECKLIST; const pm_char STR_VIEW_NOTES[] PROGMEM = TR_VIEW_NOTES; -const pm_char STR_MODEL_SELECT[] PROGMEM = TR_MODEL_SELECT; + const pm_char STR_MODEL_SELECT[] PROGMEM = TR_MODEL_SELECT; const pm_char STR_RESET_SUBMENU[] PROGMEM = TR_RESET_SUBMENU; const pm_char STR_LOWALARM[] PROGMEM = TR_LOWALARM; const pm_char STR_CRITICALALARM[] PROGMEM = TR_CRITICALALARM; + const pm_char STR_RSSIALARM_WARN[] PROGMEM = TR_RSSIALARM_WARN; + const pm_char STR_NO_RSSIALARM[] PROGMEM = TR_NO_RSSIALARM; + const pm_char STR_DISABLE_ALARM[] PROGMEM = TR_DISABLE_ALARM; const pm_char STR_TELEMETRY_TYPE[] PROGMEM = TR_TELEMETRY_TYPE; const pm_char STR_TELEMETRY_SENSORS[] PROGMEM = TR_TELEMETRY_SENSORS; const pm_char STR_VALUE[] PROGMEM = TR_VALUE; @@ -650,6 +683,7 @@ const pm_char STR_ADDMAINVIEW[] PROGMEM = TR_ADDMAINVIEW; const pm_char STR_BACKGROUND_COLOR[] PROGMEM = TR_BACKGROUND_COLOR; const pm_char STR_MAIN_COLOR[] PROGMEM = TR_MAIN_COLOR; + const pm_char STR_MULTI_RFPOWER[] PROGMEM = TR_MULTI_RFPOWER; #endif #if defined(CPUARM) @@ -713,6 +747,10 @@ const pm_char STR_MODULE_RANGE[] PROGMEM = TR_MODULE_RANGE; #endif +#if defined(BLUETOOTH) + const pm_char STR_BLUETOOTH[] PROGMEM = TR_BLUETOOTH; +#endif + #if defined(TELEMETRY_MAVLINK) const pm_char STR_MAVLINK_RC_RSSI_SCALE_LABEL[] PROGMEM = TR_MAVLINK_RC_RSSI_SCALE_LABEL; const pm_char STR_MAVLINK_PC_RSSI_EN_LABEL[] PROGMEM = TR_MAVLINK_PC_RSSI_EN_LABEL; diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/src/translations.h opentx-companion22-2.2.1~ppa01~xenial/radio/src/translations.h --- opentx-companion22-2.2.0~ppa02~xenial/radio/src/translations.h 2017-04-29 16:57:04.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/src/translations.h 2017-12-17 16:22:27.000000000 +0000 @@ -85,11 +85,15 @@ #endif #if defined(PCBHORUS) -#define TR_VTRAINERMODES TR_VTRAINER_MASTER_JACK TR_VTRAINER_SLAVE_JACK TR_VTRAINER_MASTER_BATTERY + #define TR_VTRAINERMODES TR_VTRAINER_MASTER_JACK TR_VTRAINER_SLAVE_JACK TR_VTRAINER_MASTER_BATTERY TR_VTRAINER_BLUETOOTH +#elif defined(PCBX9E) + #define TR_VTRAINERMODES TR_VTRAINER_MASTER_JACK TR_VTRAINER_SLAVE_JACK TR_VTRAINER_MASTER_SBUS_MODULE TR_VTRAINER_MASTER_CPPM_MODULE TR_VTRAINER_MASTER_BATTERY TR_VTRAINER_BLUETOOTH +#elif defined(PCBTARANIS) && defined(BLUETOOTH) + #define TR_VTRAINERMODES TR_VTRAINER_MASTER_JACK TR_VTRAINER_SLAVE_JACK TR_VTRAINER_MASTER_SBUS_MODULE TR_VTRAINER_MASTER_CPPM_MODULE TR_VTRAINER_MASTER_BATTERY TR_VTRAINER_BLUETOOTH #elif defined(PCBTARANIS) -#define TR_VTRAINERMODES TR_VTRAINER_MASTER_JACK TR_VTRAINER_SLAVE_JACK TR_VTRAINER_MASTER_SBUS_MODULE TR_VTRAINER_MASTER_CPPM_MODULE TR_VTRAINER_MASTER_BATTERY + #define TR_VTRAINERMODES TR_VTRAINER_MASTER_JACK TR_VTRAINER_SLAVE_JACK TR_VTRAINER_MASTER_SBUS_MODULE TR_VTRAINER_MASTER_CPPM_MODULE TR_VTRAINER_MASTER_BATTERY #elif defined(CPUARM) -#define TR_VTRAINERMODES TR_VTRAINER_MASTER_JACK TR_VTRAINER_SLAVE_JACK TR_VTRAINER_MASTER_CPPM_MODULE TR_VTRAINER_MASTER_BATTERY + #define TR_VTRAINERMODES TR_VTRAINER_MASTER_JACK TR_VTRAINER_SLAVE_JACK TR_VTRAINER_MASTER_CPPM_MODULE TR_VTRAINER_MASTER_BATTERY #endif #if (LCD_W == 212) @@ -173,6 +177,7 @@ #define OFS_VTEMPLATES (OFS_VTELEMCHNS + sizeof(TR_VTELEMCHNS)) #endif #if defined(TEMPLATES) + #define TR_VTEMPLATES TR_TEMPLATE_CLEAR_MIXES TR_TEMPLATE_SIMPLE_4CH TR_TEMPLATE_STICKY_TCUT TR_TEMPLATE_VTAIL TR_TEMPLATE_DELTA TR_TEMPLATE_ECCPM TR_TEMPLATE_HELI TR_TEMPLATE_SERVO_TEST #define OFS_VSWASHTYPE (OFS_VTEMPLATES + sizeof(TR_VTEMPLATES)) #else #define OFS_VSWASHTYPE (OFS_VTEMPLATES) @@ -202,21 +207,25 @@ #define OFS_VBEEPCOUNTDOWN (OFS_VUNITSSYSTEM + sizeof(TR_VUNITSSYSTEM)) #define OFS_VVARIOCENTER (OFS_VBEEPCOUNTDOWN + sizeof(TR_VBEEPCOUNTDOWN)) #define OFS_COUNTRYCODES (OFS_VVARIOCENTER + sizeof(TR_VVARIOCENTER)) + #define OFS_USBMODES (OFS_COUNTRYCODES + sizeof(TR_COUNTRYCODES)) #else #define OFS_COUNTRYCODES (OFS_VLCD) #endif #if defined(PXX) || defined(CPUARM) - #define OFS_VFAILSAFE (OFS_COUNTRYCODES + sizeof(TR_COUNTRYCODES)) + #define OFS_VFAILSAFE (OFS_USBMODES + sizeof(TR_USBMODES)) #define OFS_VTRAINERMODES (OFS_VFAILSAFE + sizeof(TR_VFAILSAFE)) #else #define OFS_VFAILSAFE (OFS_COUNTRYCODES) #define OFS_VTRAINERMODES (OFS_VFAILSAFE) #endif #if defined(CPUARM) - #define OFS_TARANIS_PROTOCOLS (OFS_VTRAINERMODES + sizeof(TR_VTRAINERMODES)) - #define OFS_TELEMETRY_PROTOCOLS (OFS_TARANIS_PROTOCOLS + sizeof(TR_TARANIS_PROTOCOLS)) - #define OFS_XJT_PROTOCOLS (OFS_TELEMETRY_PROTOCOLS + sizeof(TR_TELEMETRY_PROTOCOLS)) - #define OFS_DSM_PROTOCOLS (OFS_XJT_PROTOCOLS + sizeof(TR_XJT_PROTOCOLS)) + #define OFS_TARANIS_PROTOCOLS (OFS_VTRAINERMODES + sizeof(TR_VTRAINERMODES)) + #define OFS_R9M_MODES (OFS_TARANIS_PROTOCOLS + sizeof(TR_TARANIS_PROTOCOLS)) + #define OFS_R9M_FCC_POWER_VALUES (OFS_R9M_MODES + sizeof(TR_R9M_MODES)) + #define OFS_R9M_LBT_POWER_VALUES (OFS_R9M_FCC_POWER_VALUES + sizeof(TR_R9M_FCC_POWER_VALUES)) + #define OFS_TELEMETRY_PROTOCOLS (OFS_R9M_LBT_POWER_VALUES + sizeof(TR_R9M_LBT_POWER_VALUES)) + #define OFS_XJT_PROTOCOLS (OFS_TELEMETRY_PROTOCOLS + sizeof(TR_TELEMETRY_PROTOCOLS)) + #define OFS_DSM_PROTOCOLS (OFS_XJT_PROTOCOLS + sizeof(TR_XJT_PROTOCOLS)) #if defined(MULTIMODULE) #define OFS_MULTI_PROTOCOLS (OFS_DSM_PROTOCOLS + sizeof(TR_DSM_PROTOCOLS)) #define OFS_VOLTSRC (OFS_MULTI_PROTOCOLS + sizeof(TR_MULTI_PROTOCOLS)) @@ -228,7 +237,12 @@ #define OFS_VFORMULAS (OFS_VSENSORTYPES + sizeof(TR_VSENSORTYPES)) #define OFS_VPREC (OFS_VFORMULAS + sizeof(TR_VFORMULAS)) #define OFS_VCELLINDEX (OFS_VPREC + sizeof(TR_VPREC)) +#if defined(BLUETOOTH) + #define OFS_BLUETOOTH_MODES (OFS_VCELLINDEX + sizeof(TR_VCELLINDEX)) + #define OFS_VANTENNATYPES (OFS_BLUETOOTH_MODES + sizeof(TR_BLUETOOTH_MODES)) +#else #define OFS_VANTENNATYPES (OFS_VCELLINDEX + sizeof(TR_VCELLINDEX)) +#endif #define OFS_MAVLINK_BAUDS (OFS_VANTENNATYPES + sizeof(TR_VANTENNATYPES)) #else #define OFS_MAVLINK_BAUDS (OFS_VTRAINERMODES) @@ -330,13 +344,17 @@ #if defined(PXX) || defined(CPUARM) #define STR_COUNTRYCODES (STR_OPEN9X + OFS_COUNTRYCODES) + #define STR_USBMODES (STR_OPEN9X + OFS_USBMODES) #define STR_VFAILSAFE (STR_OPEN9X + OFS_VFAILSAFE) #endif #if defined(CPUARM) #define STR_VTRAINERMODES (STR_OPEN9X + OFS_VTRAINERMODES) #define STR_TARANIS_PROTOCOLS (STR_OPEN9X + OFS_TARANIS_PROTOCOLS) - #define STR_TELEMETRY_PROTOCOLS (STR_OPEN9X + OFS_TELEMETRY_PROTOCOLS) + #define STR_R9M_MODES (STR_OPEN9X + OFS_R9M_MODES) + #define STR_R9M_FCC_POWER_VALUES (STR_OPEN9X + OFS_R9M_FCC_POWER_VALUES) + #define STR_R9M_LBT_POWER_VALUES (STR_OPEN9X + OFS_R9M_LBT_POWER_VALUES) + #define STR_TELEMETRY_PROTOCOLS (STR_OPEN9X + OFS_TELEMETRY_PROTOCOLS) #define STR_XJT_PROTOCOLS (STR_OPEN9X + OFS_XJT_PROTOCOLS) #define STR_DSM_PROTOCOLS (STR_OPEN9X + OFS_DSM_PROTOCOLS) #if defined(MULTIMODULE) @@ -350,6 +368,11 @@ #define STR_VANTENNATYPES (STR_OPEN9X + OFS_VANTENNATYPES) #endif +#if defined(BLUETOOTH) + extern const pm_char STR_BLUETOOTH[]; + #define STR_BLUETOOTH_MODES (STR_OPEN9X + OFS_BLUETOOTH_MODES) +#endif + #if defined(TELEMETRY_MAVLINK) #define STR_MAVLINK_BAUDS (STR_OPEN9X + OFS_MAVLINK_BAUDS) #define STR_MAVLINK_AC_MODES (STR_OPEN9X + OFS_MAVLINK_AC_MODES) @@ -393,6 +416,10 @@ #endif extern const pm_char STR_PROTO[]; extern const pm_char STR_PPMFRAME[]; +#if defined(CPUARM) +extern const pm_char STR_REFRESHRATE[]; +extern const pm_char SSTR_WARN_BATTVOLTAGE[]; +#endif extern const pm_char STR_MS[]; extern const pm_char STR_SWITCH[]; extern const pm_char STR_TRIMS[]; @@ -466,6 +493,9 @@ extern const pm_char STR_INACTIVITYALARM[]; extern const pm_char STR_MEMORYWARNING[]; extern const pm_char STR_ALARMWARNING[]; +extern const pm_char STR_RSSISHUTDOWNALARM[]; +extern const pm_char STR_MODEL_STILL_POWERED[]; +extern const pm_char STR_PRESS_ENTER_TO_CONFIRM[]; extern const pm_char STR_RENAVIG[]; extern const pm_char STR_THROTTLEREVERSE[]; extern const pm_char STR_TIMER_NAME[]; @@ -580,19 +610,19 @@ extern const pm_char STR_MULTI_CUSTOM[]; extern const pm_char STR_MULTI_OPTION[]; extern const pm_char STR_MULTI_VIDFREQ[]; -extern const pm_char STR_MULTI_RFPOWER[]; extern const pm_char STR_MULTI_RFTUNE[]; extern const pm_char STR_MULTI_TELEMETRY[]; extern const pm_char STR_MULTI_AUTOBIND[]; extern const pm_char STR_MULTI_DSM_AUTODTECT[]; extern const pm_char STR_MULTI_LOWPOWER[]; -extern const pm_char STR_DISABLE_INTERNAL[]; extern const pm_char STR_MODULE_NO_SERIAL_MODE[]; extern const pm_char STR_MODULE_NO_INPUT[]; +extern const pm_char STR_MODULE_WAITFORBIND[]; extern const pm_char STR_MODULE_NO_TELEMETRY[]; extern const pm_char STR_MODULE_BINDING[]; extern const pm_char STR_PROTOCOL_INVALID[]; extern const pm_char STR_MODULE_STATUS[]; +extern const pm_char STR_MODULE_SYNC[]; extern const pm_char STR_MULTI_SERVOFREQ[]; #if LCD_W < 212 extern const pm_char STR_SUBTYPE[]; @@ -607,6 +637,7 @@ extern const pm_char STR_SYNCMENU[]; extern const pm_char STR_INTERNALRF[]; extern const pm_char STR_EXTERNALRF[]; +extern const pm_char STR_MODULE_TELEMETRY[]; extern const pm_char STR_FAILSAFE[]; extern const pm_char STR_FAILSAFESET[]; extern const pm_char STR_HOLD[]; @@ -614,6 +645,8 @@ extern const pm_char STR_MENUSENSOR[]; extern const pm_char STR_SENSOR[]; extern const pm_char STR_COUNTRYCODE[]; +extern const pm_char STR_USBMODE[]; +extern const pm_char STR_DISABLE_INTERNAL[]; #endif #if defined(TELEMETRY_FRSKY) @@ -684,6 +717,9 @@ extern const pm_char STR_RESET_TELEMETRY[]; extern const pm_char STR_STATISTICS[]; extern const pm_char STR_ABOUT_US[]; + extern const pm_char STR_USB_JOYSTICK[]; + extern const pm_char STR_USB_MASS_STORAGE[]; + extern const pm_char STR_USB_SERIAL[]; extern const pm_char STR_SETUP_SCREENS[]; extern const pm_char STR_MONITOR_SCREENS[]; #endif @@ -713,6 +749,8 @@ extern const pm_char STR_ALARMSWARN[]; extern const pm_char STR_SWITCHWARN[]; extern const pm_char STR_FAILSAFEWARN[]; +extern const pm_char STR_NIGHTLY_WARNING[]; +extern const pm_char STR_NIGHTLY_NOTSAFE[]; extern const pm_char STR_WRONG_SDCARDVERSION[]; extern const pm_char STR_WRONG_PCBREV[]; extern const pm_char STR_EMERGENCY_MODE[]; @@ -759,6 +797,7 @@ extern const pm_char STR_FORMATTING[]; extern const pm_char STR_TEMP_CALIB[]; extern const pm_char STR_TIME[]; +extern const pm_char STR_MAXBAUDRATE[]; extern const pm_char STR_BAUDRATE[]; extern const pm_char STR_SD_INFO_TITLE[]; extern const pm_char STR_SD_TYPE[]; @@ -810,6 +849,7 @@ extern const LanguagePack skLanguagePack; extern const LanguagePack seLanguagePack; extern const LanguagePack huLanguagePack; + extern const LanguagePack ruLanguagePack; extern const LanguagePack * const languagePacks[]; #if defined(LANGUAGE_PACKS_DEFINITION) const LanguagePack * const languagePacks[] = { @@ -823,6 +863,7 @@ &itLanguagePack, &plLanguagePack, &ptLanguagePack, + &ruLanguagePack, &seLanguagePack, &skLanguagePack, NULL @@ -867,7 +908,7 @@ #define TR_LIMITS_HEADERS { HINT(TR_LIMITS_HEADERS_NAME), HINT(TR_LIMITS_HEADERS_SUBTRIM), HINT(TR_LIMITS_HEADERS_MIN), HINT(TR_LIMITS_HEADERS_MAX), HINT(TR_LIMITS_HEADERS_DIRECTION), HINT(TR_LIMITS_HEADERS_CURVE), HINT(TR_LIMITS_HEADERS_PPMCENTER), HINT(TR_LIMITS_HEADERS_SUBTRIMMODE) } #define TR_LSW_HEADERS { HINT(TR_LSW_HEADERS_FUNCTION), HINT(TR_LSW_HEADERS_V1), HINT(TR_LSW_HEADERS_V2), HINT(TR_LSW_HEADERS_V2), HINT(TR_LSW_HEADERS_ANDSW), HINT(TR_LSW_HEADERS_DURATION), HINT(TR_LSW_HEADERS_DELAY) } -#define TR_GVAR_HEADERS { HINT(TR_GVAR_HEADERS_NAME), HINT(TR_GVAR_HEADERS_FM0), HINT(TR_GVAR_HEADERS_FM1), HINT(TR_GVAR_HEADERS_FM2), HINT(TR_GVAR_HEADERS_FM3), HINT(TR_GVAR_HEADERS_FM4), HINT(TR_GVAR_HEADERS_FM5), HINT(TR_GVAR_HEADERS_FM6), HINT(TR_GVAR_HEADERS_FM7), HINT(TR_GVAR_HEADERS_FM8) } +#define TR_GVAR_HEADERS { HINT(TR_GVAR_HEADERS_FM0), HINT(TR_GVAR_HEADERS_FM1), HINT(TR_GVAR_HEADERS_FM2), HINT(TR_GVAR_HEADERS_FM3), HINT(TR_GVAR_HEADERS_FM4), HINT(TR_GVAR_HEADERS_FM5), HINT(TR_GVAR_HEADERS_FM6), HINT(TR_GVAR_HEADERS_FM7), HINT(TR_GVAR_HEADERS_FM8) } #if LCD_W >= 212 extern const char * const STR_PHASES_HEADERS[]; @@ -884,6 +925,11 @@ extern const pm_char STR_BINDING_1_8_TELEM_OFF[]; extern const pm_char STR_BINDING_9_16_TELEM_ON[]; extern const pm_char STR_BINDING_9_16_TELEM_OFF[]; + extern const pm_char STR_BINDING_25MW_CH1_8_TELEM_OFF[]; + extern const pm_char STR_BINDING_25MW_CH1_8_TELEM_ON[]; + extern const pm_char STR_BINDING_500MW_CH1_8_TELEM_OFF[]; + extern const pm_char STR_BINDING_500MW_CH9_16_TELEM_OFF[]; + extern const pm_char STR_BINDING_OPTION[]; extern const pm_char STR_CHANNELRANGE[]; extern const pm_char STR_ANTENNASELECTION[]; extern const pm_char STR_ANTENNACONFIRM1[]; @@ -896,6 +942,9 @@ extern const pm_char STR_RESET_SUBMENU[]; extern const pm_char STR_LOWALARM[]; extern const pm_char STR_CRITICALALARM[]; + extern const pm_char STR_RSSIALARM_WARN[]; + extern const pm_char STR_NO_RSSIALARM[]; + extern const pm_char STR_DISABLE_ALARM[]; extern const pm_char STR_TELEMETRY_TYPE[]; extern const pm_char STR_TELEMETRY_SENSORS[]; extern const pm_char STR_VALUE[]; @@ -938,6 +987,7 @@ extern const pm_char STR_ADDMAINVIEW[]; extern const pm_char STR_BACKGROUND_COLOR[]; extern const pm_char STR_MAIN_COLOR[]; + extern const pm_char STR_MULTI_RFPOWER[]; #endif #if defined(CPUARM) diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/util/build-firmware.py opentx-companion22-2.2.1~ppa01~xenial/radio/util/build-firmware.py --- opentx-companion22-2.2.0~ppa02~xenial/radio/util/build-firmware.py 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/util/build-firmware.py 2017-11-20 18:44:06.000000000 +0000 @@ -1,5 +1,6 @@ #!/usr/bin/env python +from __future__ import print_function import os import sys import subprocess @@ -194,7 +195,10 @@ for opt, value in command_options.items(): cmd.append("-D%s=%s" % (opt, value)) if "OPENTX_VERSION_SUFFIX" in os.environ: - cmd.append('-DVERSION_SUFFIX="%s"' % os.environ["OPENTX_VERSION_SUFFIX"]) + suffix = os.environ["OPENTX_VERSION_SUFFIX"] + cmd.append('-DVERSION_SUFFIX="%s"' % suffix) + if suffix.startswith("N"): + cmd.append('-DNIGHTLY_BUILD_WARNING=YES') cmd.append(srcdir) proc = subprocess.Popen(cmd, stdout=subprocess.PIPE, stderr=subprocess.PIPE) output, error = proc.communicate() @@ -202,7 +206,7 @@ file(outpath, "a").write("\n".join(cmd) + output + error) else: file(errpath, "w").write(output + error) - print filename + print(filename) exit(COMPILATION_ERROR) # Launch make @@ -213,7 +217,7 @@ file(outpath, "a").write(output + error) else: file(errpath, "w").write(output + error) - print filename + print(filename) exit(COMPILATION_ERROR) if what == "firmware": @@ -230,11 +234,11 @@ shutil.move(target, path) if os.path.isfile(errpath): - print filename + print(filename) exit(COMPILATION_ERROR) if os.path.isfile(path): - print filename + print(filename) exit(0) lockpath = path + ".lock" @@ -244,8 +248,8 @@ if not os.path.isfile(path): build_firmware(path) except filelock.Timeout: - print filename + print(filename) exit(COMPILATION_ERROR) -print filename +print(filename) exit(0) diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/util/checksize.py opentx-companion22-2.2.1~ppa01~xenial/radio/util/checksize.py --- opentx-companion22-2.2.0~ppa02~xenial/radio/util/checksize.py 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/util/checksize.py 2017-11-20 18:44:06.000000000 +0000 @@ -6,6 +6,7 @@ # on 2.2 release: cmake -DPCB=9X -DTELEMETRY=FRSKY -DAUDIO=YES -DVOICE=YES -DHELI=YES -DTEMPLATES=YES ~/git/opentx # => 64828 (program) + 3236 (data) +from __future__ import print_function import os import sys import subprocess @@ -26,7 +27,7 @@ proc = subprocess.Popen(cmd, stdout=subprocess.PIPE, stderr=subprocess.PIPE) output, error = proc.communicate() if proc.returncode != 0: - print "HEAD~%d git reset failed" % index + print("HEAD~%d git reset failed" % index) continue os.chdir(buildir) @@ -34,14 +35,14 @@ proc = subprocess.Popen(cmd, stdout=subprocess.PIPE, stderr=subprocess.PIPE) output, error = proc.communicate() if proc.returncode != 0: - print "HEAD~%d cmake failed" % index + print("HEAD~%d cmake failed" % index) continue cmd = ["make", "-j4", "firmware"] proc = subprocess.Popen(cmd, stdout=subprocess.PIPE, stderr=subprocess.PIPE) output, error = proc.communicate() if proc.returncode != 0: - print "HEAD~%d make firmware failed" % index + print("HEAD~%d make firmware failed" % index) continue if os.path.isfile("firmware.bin"): @@ -50,11 +51,11 @@ oldsize = int(subprocess.check_output('avr-size -A firmware.hex | grep Total | cut -f2- -d " "', shell=True)) if size: if size > oldsize: - print "HEAD~%d %d: increase by %d bytes" % (index-1, size, size-oldsize) + print("HEAD~%d %d: increase by %d bytes" % (index-1, size, size-oldsize)) elif size < oldsize: - print "HEAD~%d %d: decrease by %d bytes" % (index-1, size, oldsize-size) + print("HEAD~%d %d: decrease by %d bytes" % (index-1, size, oldsize-size)) else: - print "HEAD~%d %d" % (index-1, size) + print("HEAD~%d %d" % (index-1, size)) size = oldsize diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/util/crossfire-parse.py opentx-companion22-2.2.1~ppa01~xenial/radio/util/crossfire-parse.py --- opentx-companion22-2.2.0~ppa02~xenial/radio/util/crossfire-parse.py 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/util/crossfire-parse.py 2017-10-31 16:16:44.000000000 +0000 @@ -33,8 +33,48 @@ data = data[:maxLen] return " ".join("{:02x}".format(c) for c in data) -def CheckCrc(packet): - return True + +# CRC8 implementation with polynom = x^8+x^7+x^6+x^4+x^2+1 (0xD5) +crc8tab = [ + 0x00, 0xD5, 0x7F, 0xAA, 0xFE, 0x2B, 0x81, 0x54, + 0x29, 0xFC, 0x56, 0x83, 0xD7, 0x02, 0xA8, 0x7D, + 0x52, 0x87, 0x2D, 0xF8, 0xAC, 0x79, 0xD3, 0x06, + 0x7B, 0xAE, 0x04, 0xD1, 0x85, 0x50, 0xFA, 0x2F, + 0xA4, 0x71, 0xDB, 0x0E, 0x5A, 0x8F, 0x25, 0xF0, + 0x8D, 0x58, 0xF2, 0x27, 0x73, 0xA6, 0x0C, 0xD9, + 0xF6, 0x23, 0x89, 0x5C, 0x08, 0xDD, 0x77, 0xA2, + 0xDF, 0x0A, 0xA0, 0x75, 0x21, 0xF4, 0x5E, 0x8B, + 0x9D, 0x48, 0xE2, 0x37, 0x63, 0xB6, 0x1C, 0xC9, + 0xB4, 0x61, 0xCB, 0x1E, 0x4A, 0x9F, 0x35, 0xE0, + 0xCF, 0x1A, 0xB0, 0x65, 0x31, 0xE4, 0x4E, 0x9B, + 0xE6, 0x33, 0x99, 0x4C, 0x18, 0xCD, 0x67, 0xB2, + 0x39, 0xEC, 0x46, 0x93, 0xC7, 0x12, 0xB8, 0x6D, + 0x10, 0xC5, 0x6F, 0xBA, 0xEE, 0x3B, 0x91, 0x44, + 0x6B, 0xBE, 0x14, 0xC1, 0x95, 0x40, 0xEA, 0x3F, + 0x42, 0x97, 0x3D, 0xE8, 0xBC, 0x69, 0xC3, 0x16, + 0xEF, 0x3A, 0x90, 0x45, 0x11, 0xC4, 0x6E, 0xBB, + 0xC6, 0x13, 0xB9, 0x6C, 0x38, 0xED, 0x47, 0x92, + 0xBD, 0x68, 0xC2, 0x17, 0x43, 0x96, 0x3C, 0xE9, + 0x94, 0x41, 0xEB, 0x3E, 0x6A, 0xBF, 0x15, 0xC0, + 0x4B, 0x9E, 0x34, 0xE1, 0xB5, 0x60, 0xCA, 0x1F, + 0x62, 0xB7, 0x1D, 0xC8, 0x9C, 0x49, 0xE3, 0x36, + 0x19, 0xCC, 0x66, 0xB3, 0xE7, 0x32, 0x98, 0x4D, + 0x30, 0xE5, 0x4F, 0x9A, 0xCE, 0x1B, 0xB1, 0x64, + 0x72, 0xA7, 0x0D, 0xD8, 0x8C, 0x59, 0xF3, 0x26, + 0x5B, 0x8E, 0x24, 0xF1, 0xA5, 0x70, 0xDA, 0x0F, + 0x20, 0xF5, 0x5F, 0x8A, 0xDE, 0x0B, 0xA1, 0x74, + 0x09, 0xDC, 0x76, 0xA3, 0xF7, 0x22, 0x88, 0x5D, + 0xD6, 0x03, 0xA9, 0x7C, 0x28, 0xFD, 0x57, 0x82, + 0xFF, 0x2A, 0x80, 0x55, 0x01, 0xD4, 0x7E, 0xAB, + 0x84, 0x51, 0xFB, 0x2E, 0x7A, 0xAF, 0x05, 0xD0, + 0xAD, 0x78, 0xD2, 0x07, 0x53, 0x86, 0x2C, 0xF9 +] + +def crc8(buffer): + crc = 0 + for c in buffer: + crc = crc8tab[crc ^ c] + return crc def ParseGPS(payload): pass @@ -95,10 +135,13 @@ ) def ParsePacket(packet): - len = packet[1] + length = packet[1] command = packet[2] payload = packet[3:-1] crc = packet[-1] + if crc != crc8(packet[2:-1]): + print("[%s]" % timeData, dump(packet), "[CRC error]") + return for id, parser in parsers: if id == command: print("[%s]" % timeData, dump(packet), parser(payload)) @@ -120,8 +163,8 @@ continue length = crossfireDataBuff[1] if length < 2 or length > 0x40: - print("Skipped 2 bytes", dump(crossfireDataBuff[:2])) - crossfireDataBuff = crossfireDataBuff[2:] + print("Skipped 1 bytex", dump(crossfireDataBuff[:1])) + crossfireDataBuff = crossfireDataBuff[1:] continue if len(crossfireDataBuff) < length+2: break diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/util/font2png.py opentx-companion22-2.2.1~ppa01~xenial/radio/util/font2png.py --- opentx-companion22-2.2.0~ppa02~xenial/radio/util/font2png.py 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/util/font2png.py 2017-10-31 16:16:44.000000000 +0000 @@ -2,7 +2,11 @@ # -*- coding: utf-8 -*- import sys -from PyQt4 import Qt, QtCore, QtGui +try: + from PyQt5 import Qt, QtGui, QtCore +except: + from PyQt4 import Qt, QtGui, QtCore + import glob app = Qt.QApplication(sys.argv) diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/util/fwoptions.py opentx-companion22-2.2.1~ppa01~xenial/radio/util/fwoptions.py --- opentx-companion22-2.2.0~ppa02~xenial/radio/util/fwoptions.py 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/util/fwoptions.py 2017-12-17 16:22:27.000000000 +0000 @@ -242,13 +242,10 @@ "faimode": ("FAI", "YES", None), "faichoice": ("FAI", "CHOICE", None), "nooverridech": ("OVERRIDE_CHANNEL_FUNCTION", "NO", "YES"), - "massstorage": ("USB", "MASSSTORAGE", None), - "cli": ("USB", "SERIAL", None), "internalppm": ("TARANIS_INTERNAL_PPM", "YES", "NO"), "shutdownconfirm": ("SHUTDOWN_CONFIRMATION", "YES", "NO"), "eu": ("SUPPORT_D16_EU_ONLY", "YES", "NO"), - "multimodule": ("MULTIMODULE", "YES", "NO"), - "bindopt": ("BINDING_OPTIONS", "YES", "NO") + "multimodule": ("MULTIMODULE", "YES", "NO") } options_taranisplus = { @@ -262,13 +259,10 @@ "faimode": ("FAI", "YES", None), "faichoice": ("FAI", "CHOICE", None), "nooverridech": ("OVERRIDE_CHANNEL_FUNCTION", "NO", "YES"), - "massstorage": ("USB", "MASSSTORAGE", None), - "cli": ("USB", "SERIAL", None), "internalppm": ("TARANIS_INTERNAL_PPM", "YES", "NO"), "shutdownconfirm": ("SHUTDOWN_CONFIRMATION", "YES", "NO"), "eu": ("SUPPORT_D16_EU_ONLY", "YES", "NO"), - "multimodule": ("MULTIMODULE", "YES", "NO"), - "bindopt": ("BINDING_OPTIONS", "YES", "NO") + "multimodule": ("MULTIMODULE", "YES", "NO") } options_taranisx9e = { @@ -282,14 +276,11 @@ "faimode": ("FAI", "YES", None), "faichoice": ("FAI", "CHOICE", None), "nooverridech": ("OVERRIDE_CHANNEL_FUNCTION", "NO", "YES"), - "massstorage": ("USB", "MASSSTORAGE", None), - "cli": ("USB", "SERIAL", None), "internalppm": ("TARANIS_INTERNAL_PPM", "YES", "NO"), "shutdownconfirm": ("SHUTDOWN_CONFIRMATION", "YES", "NO"), "eu": ("SUPPORT_D16_EU_ONLY", "YES", "NO"), "horussticks": ("STICKS", "HORUS", "STANDARD"), - "multimodule": ("MULTIMODULE", "YES", "NO"), - "bindopt": ("BINDING_OPTIONS", "YES", "NO") + "multimodule": ("MULTIMODULE", "YES", "NO") } options_x12s = { @@ -301,12 +292,9 @@ "faimode": ("FAI", "YES", None), "faichoice": ("FAI", "CHOICE", None), "nooverridech": ("OVERRIDE_CHANNEL_FUNCTION", "NO", "YES"), - "massstorage": ("USB", "MASSSTORAGE", None), - "cli": ("USB", "SERIAL", None), "eu": ("SUPPORT_D16_EU_ONLY", "YES", "NO"), "multimodule": ("MULTIMODULE", "YES", "NO"), - "pcbdev": ("PCBREV", "10", None), - "bindopt": ("BINDING_OPTIONS", "YES", "NO") + "pcbdev": ("PCBREV", "10", None) } options_x10 = { @@ -318,9 +306,6 @@ "faimode": ("FAI", "YES", None), "faichoice": ("FAI", "CHOICE", None), "nooverridech": ("OVERRIDE_CHANNEL_FUNCTION", "NO", "YES"), - "massstorage": ("USB", "MASSSTORAGE", None), - "cli": ("USB", "SERIAL", None), "eu": ("SUPPORT_D16_EU_ONLY", "YES", "NO"), - "multimodule": ("MULTIMODULE", "YES", "NO"), - "bindopt": ("BINDING_OPTIONS", "YES", "NO") + "multimodule": ("MULTIMODULE", "YES", "NO") } diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/util/lua_trace2plot.py opentx-companion22-2.2.1~ppa01~xenial/radio/util/lua_trace2plot.py --- opentx-companion22-2.2.0~ppa02~xenial/radio/util/lua_trace2plot.py 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/util/lua_trace2plot.py 2017-11-11 11:29:14.000000000 +0000 @@ -0,0 +1,55 @@ +#!/usr/bin/env python +# -*- coding: utf-8 -*- + +""" + This script parses debug log events related to Lua memory (de)allocations ( lines + starting wiht "LT: ") and produces a data for gnuplot program + + Usage: + + ./simu 2>&1 | grep "^LT" | ../radio/util/lua_trace2plot.py > data.plot + gnuplot -e 'set xtics rotate; plot "data.plot" using 2:xtic(1) ; pause mouse close' +""" + +from __future__ import print_function + +import sys + + +if len(sys.argv) > 1: + inputFile = sys.argv[1] + inp = open(inputFile, "r") +else: + inp = sys.stdin + + +x = 0 +memUsed = 0 +while True: + skip = True + line = inp.readline() + if len(line) == 0: + break + line = line.strip('\r\n') + if len(line) == 0: + skip = True + if line.startswith("LT:"): + skip = False + + if not skip: + parts = line.split() + if len(parts) >= 3: + data = parts[1].strip("[").strip("]").split(",") + alloc = int(data[0]) + free = int(data[1]) + line = parts[2] + if alloc > 0: + memUsed += alloc + print("'%s'\t%d" % (line, memUsed)) + x += 1 + if free < 0: + memUsed += free + print("'%s'\t%d" % (line, memUsed)) + x += 1 + +inp.close() diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/util/taranisicons.py opentx-companion22-2.2.1~ppa01~xenial/radio/util/taranisicons.py --- opentx-companion22-2.2.0~ppa02~xenial/radio/util/taranisicons.py 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/util/taranisicons.py 2017-10-31 16:16:44.000000000 +0000 @@ -1,7 +1,9 @@ #!/usr/bin/env python # -*- coding: utf-8 -*- - -from PyQt4 import Qt, QtGui +try: + from PyQt5 import Qt, QtGui +except: + from PyQt4 import Qt, QtGui menu = ["radio_setup", "model_select", "model_settings", "model_checklist", "files", "version"] diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/util/tts_cz.py opentx-companion22-2.2.1~ppa01~xenial/radio/util/tts_cz.py --- opentx-companion22-2.2.0~ppa02~xenial/radio/util/tts_cz.py 2017-05-14 17:18:57.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/util/tts_cz.py 2017-10-31 16:16:44.000000000 +0000 @@ -78,6 +78,7 @@ ("senzor ztracen", "sensorko", NO_ALTERNATE), ("servo přetíženo", "servoko", NO_ALTERNATE), ("r f přebuzeno", "rxko", NO_ALTERNATE), + ("receiver still connected", "modelpwr", NO_ALTERNATE), ]: systemSounds.append((s, filename(f, a))) for i, (s, f) in enumerate([("podvozek je zasunut", "podvo0"), diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/util/tts_de.py opentx-companion22-2.2.1~ppa01~xenial/radio/util/tts_de.py --- opentx-companion22-2.2.0~ppa02~xenial/radio/util/tts_de.py 2017-05-14 17:18:57.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/util/tts_de.py 2017-10-31 16:16:44.000000000 +0000 @@ -74,6 +74,9 @@ ("Telemetrie wiederhergestellt", "telemok", NO_ALTERNATE), ("Schülersignal verloren", "trainko", NO_ALTERNATE), ("Schülersignal wiederhergestellt", "trainok", NO_ALTERNATE), + ("servo overload", "servoko", NO_ALTERNATE), + ("power overload", "rxko", NO_ALTERNATE), + ("Empfänger noch verbunden", "modelpwr", NO_ALTERNATE), ]: systemSounds.append((s, filename(f, a))) for i, s in enumerate(["Uhr", "Uhr", "Sender", "Empfang", "A1", "A2", "Hoehe", "Motor", diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/util/tts_en.py opentx-companion22-2.2.1~ppa01~xenial/radio/util/tts_en.py --- opentx-companion22-2.2.0~ppa02~xenial/radio/util/tts_en.py 2017-05-14 17:18:57.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/util/tts_en.py 2017-10-31 16:16:44.000000000 +0000 @@ -68,6 +68,7 @@ ("sensor lost", "sensorko", NO_ALTERNATE), ("servo overload", "servoko", NO_ALTERNATE), ("power overload", "rxko", NO_ALTERNATE), + ("receiver still connected", "modelpwr", NO_ALTERNATE), ]: systemSounds.append((s, filename(f, a))) for i, (s, f) in enumerate([("gear!, up!", "gearup"), diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/util/tts_es.py opentx-companion22-2.2.1~ppa01~xenial/radio/util/tts_es.py --- opentx-companion22-2.2.0~ppa02~xenial/radio/util/tts_es.py 2017-05-14 17:18:57.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/util/tts_es.py 2017-10-31 16:16:44.000000000 +0000 @@ -74,6 +74,9 @@ ("Problemas con la antena del transmisor", "swr_red", NO_ALTERNATE), ("Sin telemetría", "telemko", NO_ALTERNATE), ("Telemetría disponible", "telemok", NO_ALTERNATE), + ("servo overload", "servoko", NO_ALTERNATE), + ("power overload", "rxko", NO_ALTERNATE), + ("receiver still connected", "modelpwr", NO_ALTERNATE), ]: systemSounds.append((s, filename(f, a))) for i, s in enumerate(["cronómetro", "cronómetro", "transmisión", "recepción", "A1", "A2", "altitud", "motor", diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/util/tts_fr.py opentx-companion22-2.2.1~ppa01~xenial/radio/util/tts_fr.py --- opentx-companion22-2.2.0~ppa02~xenial/radio/util/tts_fr.py 2017-05-14 17:18:57.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/util/tts_fr.py 2017-10-31 16:16:44.000000000 +0000 @@ -67,6 +67,7 @@ ("Sonde de télémétrie perdue", "sensorko", NO_ALTERNATE), ("Servo en surcharge", "servoko", NO_ALTERNATE), ("Surcharge réception", "rxko", NO_ALTERNATE), + ("Récepteur encore sous tension", "modelpwr", NO_ALTERNATE), ]: systemSounds.append((s, filename(f, a))) for i, (s, f) in enumerate([("altitude", "altitude"), diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/util/tts_it.py opentx-companion22-2.2.1~ppa01~xenial/radio/util/tts_it.py --- opentx-companion22-2.2.0~ppa02~xenial/radio/util/tts_it.py 2017-05-14 17:18:57.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/util/tts_it.py 2017-10-31 16:16:44.000000000 +0000 @@ -70,6 +70,9 @@ ("Problema all'antenna della radio", "swr_red", NO_ALTERNATE), ("Telemetria assente", "telemko", NO_ALTERNATE), ("Telemetria disponibile", "telemok", NO_ALTERNATE), + ("servo overload", "servoko", NO_ALTERNATE), + ("power overload", "rxko", NO_ALTERNATE), + ("receiver still connected", "modelpwr", NO_ALTERNATE), ]: systemSounds.append((s, filename(f, a))) for i, s in enumerate(["timer", "", "tensione", "tensione", "trasmissione", "ricezione", "altitudine", "motore", diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/util/tts_pt.py opentx-companion22-2.2.1~ppa01~xenial/radio/util/tts_pt.py --- opentx-companion22-2.2.0~ppa02~xenial/radio/util/tts_pt.py 2017-05-14 17:18:57.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/util/tts_pt.py 2017-10-31 16:16:44.000000000 +0000 @@ -72,6 +72,9 @@ ("recepção de sinal muito baixa", "rssi_org", NO_ALTERNATE), ("recepção de sinal crítica", "rssi_red", NO_ALTERNATE), ("Problema com a antena do transmissor", "swr_red", NO_ALTERNATE), + ("servo overload", "servoko", NO_ALTERNATE), + ("power overload", "rxko", NO_ALTERNATE), + ("receiver still connected", "modelpwr", NO_ALTERNATE), ]: systemSounds.append((s, filename(f, a))) for i, s in enumerate(["cronómetro", "cronómetro", "transmissão", "recepção", "A1", "A2", "altitude", "motor", diff -Nru opentx-companion22-2.2.0~ppa02~xenial/radio/util/voices_ru.psv opentx-companion22-2.2.1~ppa01~xenial/radio/util/voices_ru.psv --- opentx-companion22-2.2.0~ppa02~xenial/radio/util/voices_ru.psv 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/radio/util/voices_ru.psv 2017-12-17 16:22:27.000000000 +0000 @@ -0,0 +1,272 @@ +SYSTEM|0000|0 +SYSTEM|0001|1 +SYSTEM|0002|2 +SYSTEM|0003|3 +SYSTEM|0004|4 +SYSTEM|0005|5 +SYSTEM|0006|6 +SYSTEM|0007|7 +SYSTEM|0008|8 +SYSTEM|0009|9 +SYSTEM|0010|10 +SYSTEM|0011|11 +SYSTEM|0012|12 +SYSTEM|0013|13 +SYSTEM|0014|14 +SYSTEM|0015|15 +SYSTEM|0016|16 +SYSTEM|0017|17 +SYSTEM|0018|18 +SYSTEM|0019|19 +SYSTEM|0020|20 +SYSTEM|0021|21 +SYSTEM|0022|22 +SYSTEM|0023|23 +SYSTEM|0024|24 +SYSTEM|0025|25 +SYSTEM|0026|26 +SYSTEM|0027|27 +SYSTEM|0028|28 +SYSTEM|0029|29 +SYSTEM|0030|30 +SYSTEM|0031|31 +SYSTEM|0032|32 +SYSTEM|0033|33 +SYSTEM|0034|34 +SYSTEM|0035|35 +SYSTEM|0036|36 +SYSTEM|0037|37 +SYSTEM|0038|38 +SYSTEM|0039|39 +SYSTEM|0040|40 +SYSTEM|0041|41 +SYSTEM|0042|42 +SYSTEM|0043|43 +SYSTEM|0044|44 +SYSTEM|0045|45 +SYSTEM|0046|46 +SYSTEM|0047|47 +SYSTEM|0048|48 +SYSTEM|0049|49 +SYSTEM|0050|50 +SYSTEM|0051|51 +SYSTEM|0052|52 +SYSTEM|0053|53 +SYSTEM|0054|54 +SYSTEM|0055|55 +SYSTEM|0056|56 +SYSTEM|0057|57 +SYSTEM|0058|58 +SYSTEM|0059|59 +SYSTEM|0060|60 +SYSTEM|0061|61 +SYSTEM|0062|62 +SYSTEM|0063|63 +SYSTEM|0064|64 +SYSTEM|0065|65 +SYSTEM|0066|66 +SYSTEM|0067|67 +SYSTEM|0068|68 +SYSTEM|0069|69 +SYSTEM|0070|70 +SYSTEM|0071|71 +SYSTEM|0072|72 +SYSTEM|0073|73 +SYSTEM|0074|74 +SYSTEM|0075|75 +SYSTEM|0076|76 +SYSTEM|0077|77 +SYSTEM|0078|78 +SYSTEM|0079|79 +SYSTEM|0080|80 +SYSTEM|0081|81 +SYSTEM|0082|82 +SYSTEM|0083|83 +SYSTEM|0084|84 +SYSTEM|0085|85 +SYSTEM|0086|86 +SYSTEM|0087|87 +SYSTEM|0088|88 +SYSTEM|0089|89 +SYSTEM|0090|90 +SYSTEM|0091|91 +SYSTEM|0092|92 +SYSTEM|0093|93 +SYSTEM|0094|94 +SYSTEM|0095|95 +SYSTEM|0096|96 +SYSTEM|0097|97 +SYSTEM|0098|98 +SYSTEM|0099|99 +SYSTEM|0100|100 +SYSTEM|0101|200 +SYSTEM|0102|300 +SYSTEM|0103|400 +SYSTEM|0104|500 +SYSTEM|0105|600 +SYSTEM|0106|700 +SYSTEM|0107|800 +SYSTEM|0108|900 +SYSTEM|0109|1000 +SYSTEM|0110| +SYSTEM|0111| +SYSTEM|0112| +SYSTEM|0165| +SYSTEM|0166| +SYSTEM|0167| +SYSTEM|0168| +SYSTEM|0169| +SYSTEM|0170| +SYSTEM|0171| +SYSTEM|0172| +SYSTEM|0173| +SYSTEM|0174| +SYSTEM|volt0| +SYSTEM|volt1| +SYSTEM|volt2| +SYSTEM|volt5| +SYSTEM|amp0| +SYSTEM|amp1| +SYSTEM|amp2| +SYSTEM|amp5| +SYSTEM|mamp0| +SYSTEM|mamp1| +SYSTEM|mamp2| +SYSTEM|mamp5| +SYSTEM|knot0| +SYSTEM|knot1| +SYSTEM|knot2| +SYSTEM|knot5| +SYSTEM|mps0| +SYSTEM|mps1| +SYSTEM|mps2| +SYSTEM|mps5| +SYSTEM|celsius0| +SYSTEM|celsius1| +SYSTEM|celsius2| +SYSTEM|celsius5| +SYSTEM|db0| +SYSTEM|db1| +SYSTEM|db2| +SYSTEM|db5| +SYSTEM|degree0| +SYSTEM|degree1| +SYSTEM|degree2| +SYSTEM|degree5| +SYSTEM|fahr0| +SYSTEM|fahr1| +SYSTEM|fahr2| +SYSTEM|fahr5| +SYSTEM|foot0| +SYSTEM|foot1| +SYSTEM|foot2| +SYSTEM|foot5| +SYSTEM|founce0| +SYSTEM|founce1| +SYSTEM|founce2| +SYSTEM|founce5| +SYSTEM|fps0| +SYSTEM|fps1| +SYSTEM|fps2| +SYSTEM|fps5| +SYSTEM|g0| +SYSTEM|g1| +SYSTEM|g2| +SYSTEM|g5| +SYSTEM|hour0| +SYSTEM|hour1| +SYSTEM|hour2| +SYSTEM|hour5| +SYSTEM|kph0| +SYSTEM|kph1| +SYSTEM|kph2| +SYSTEM|kph5| +SYSTEM|mamph0| +SYSTEM|mamph1| +SYSTEM|mamph2| +SYSTEM|mamph5| +SYSTEM|meter0| +SYSTEM|meter1| +SYSTEM|meter2| +SYSTEM|meter5| +SYSTEM|minute0| +SYSTEM|minute1| +SYSTEM|minute2| +SYSTEM|minute5| +SYSTEM|ml0| +SYSTEM|ml1| +SYSTEM|ml2| +SYSTEM|ml5| +SYSTEM|mph0| +SYSTEM|mph1| +SYSTEM|mph2| +SYSTEM|mph5| +SYSTEM|mwatt0| +SYSTEM|mwatt1| +SYSTEM|mwatt2| +SYSTEM|mwatt5| +SYSTEM|percent0| +SYSTEM|percent1| +SYSTEM|percent2| +SYSTEM|percent5| +SYSTEM|radian0| +SYSTEM|radian1| +SYSTEM|radian2| +SYSTEM|radian5| +SYSTEM|rpm0| +SYSTEM|rpm1| +SYSTEM|rpm2| +SYSTEM|rpm5| +SYSTEM|second0| +SYSTEM|second1| +SYSTEM|second2| +SYSTEM|second5| +SYSTEM|watt0| +SYSTEM|watt1| +SYSTEM|watt2| +SYSTEM|watt5| +SYSTEM|eebad| +SYSTEM|hello| ! +SYSTEM|inactiv| ! ! +SYSTEM|lowbatt| +SYSTEM|maxtrim| +SYSTEM|midtrim| +SYSTEM|mintrim| +SYSTEM|rssi_org| ! +SYSTEM|rssi_red| ! +SYSTEM|rxko| +SYSTEM|sensorko| +SYSTEM|servoko| +SYSTEM|swalert| ! +SYSTEM|swr_red| ! +SYSTEM|telemko| +SYSTEM|telemok| +SYSTEM|thralert| ! +SYSTEM|timovr1| 1. +SYSTEM|timovr2| 2. +SYSTEM|timovr3| 3. +SYSTEM|trainko| +SYSTEM|trainok| +SYSTEM|0180| +SYSTEM|0181| +SYSTEM|0182| +SYSTEM|0183| +SYSTEM|0184| +SYSTEM|0185| +SYSTEM|0186| +SYSTEM|0187| +SYSTEM|0188| +SYSTEM|0189| +SYSTEM|0190| +SYSTEM|0191| +SYSTEM|0192| +SYSTEM|0193| +SYSTEM|0194| +SYSTEM|0195| +SYSTEM|0196| +SYSTEM|0197| +SYSTEM|0198| +SYSTEM|0199| +SYSTEM|0200| +SYSTEM|0201| +SYSTEM|0202| diff -Nru opentx-companion22-2.2.0~ppa02~xenial/README.md opentx-companion22-2.2.1~ppa01~xenial/README.md --- opentx-companion22-2.2.0~ppa02~xenial/README.md 2017-05-14 17:18:57.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/README.md 2017-12-17 16:22:27.000000000 +0000 @@ -1,7 +1,7 @@ ## OpenTX 2.2 Branch -[![Build Status](https://travis-ci.org/opentx/opentx.svg?branch=next)](https://travis-ci.org/opentx/opentx) -[![Coverity Scan Build Status](https://scan.coverity.com/projects/11787/badge.svg)](https://scan.coverity.com/projects/opentx-opentx) +[![Travis build Status](https://travis-ci.org/opentx/opentx.svg?branch=2.2)](https://travis-ci.org/opentx/opentx) +[![Quality Gate](https://sonarcloud.io/api/badges/gate?key=OpenTX:2.2)](https://sonarcloud.io/dashboard?id=OpenTX:2.2) [![Join the chat at https://opentx.rocket.chat](https://camo.githubusercontent.com/3d659054abd6ce21c0e47cf3b83a51bda69ca282/68747470733a2f2f64656d6f2e726f636b65742e636861742f696d616765732f6a6f696e2d636861742e737667)](https://opentx.rocket.chat) [![Donate using Paypal](https://img.shields.io/badge/paypal-donate-yellow.svg)](https://www.paypal.com/cgi-bin/webscr?cmd=_s-xclick&hosted_button_id=DJ9MASSKVW8WN) diff -Nru opentx-companion22-2.2.0~ppa02~xenial/sonar-project.properties opentx-companion22-2.2.1~ppa01~xenial/sonar-project.properties --- opentx-companion22-2.2.0~ppa02~xenial/sonar-project.properties 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/sonar-project.properties 2017-11-20 18:44:06.000000000 +0000 @@ -0,0 +1,9 @@ +sonar.host.url = https://sonarcloud.io +sonar.projectKey = OpenTX +sonar.organization = opentx-github +sonar.projectName = OpenTX +sonar.projectVersion = 2.2 +sonar.sources = . +sonar.exclusions = sound/**, build/**, radio/src/thirdparty/** +sonar.cfamily.build-wrapper-output = bw_output + diff -Nru opentx-companion22-2.2.0~ppa02~xenial/tools/build-companion-nightly.sh opentx-companion22-2.2.1~ppa01~xenial/tools/build-companion-nightly.sh --- opentx-companion22-2.2.0~ppa02~xenial/tools/build-companion-nightly.sh 2017-05-14 17:18:57.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/tools/build-companion-nightly.sh 2017-10-31 16:16:33.000000000 +0000 @@ -25,7 +25,7 @@ SRCDIR=$1 OUTDIR=$2 -COMMON_OPTIONS="-DALLOW_NIGHTLY_BUILDS=YES -DGVARS=YES -DHELI=YES -DLUA=YES -DMULTIMODULE=YES -DTELEMETRY=FRSKY -DPPM_LIMITS_SYMETRICAL=YES -DVARIO=YES -DGAUGES=YES -DAUTOSWITCH=YES -DAUTOSOURCE=YES -DAUDIO=YES -DGPS=YES -DPPM_CENTER_ADJUSTABLE=YES -DFLIGHT_MODES=YES -DOVERRIDE_CHANNEL_FUNCTION=YES -DFRSKY_STICKS=YES" +COMMON_OPTIONS="-DALLOW_NIGHTLY_BUILDS=YES -DNIGHTLY_BUILD_WARNING=YES -DGVARS=YES -DHELI=YES -DLUA=YES -DMULTIMODULE=YES -DTELEMETRY=FRSKY -DPPM_LIMITS_SYMETRICAL=YES -DVARIO=YES -DGAUGES=YES -DAUTOSWITCH=YES -DAUTOSOURCE=YES -DAUDIO=YES -DGPS=YES -DPPM_CENTER_ADJUSTABLE=YES -DFLIGHT_MODES=YES -DOVERRIDE_CHANNEL_FUNCTION=YES -DFRSKY_STICKS=YES" if [ "$(uname)" = "Darwin" ]; then COMMON_OPTIONS="${COMMON_OPTIONS} -DCMAKE_PREFIX_PATH=~/Qt/5.7/clang_64/ -DCMAKE_OSX_DEPLOYMENT_TARGET='10.9'" fi @@ -65,6 +65,9 @@ cmake ${COMMON_OPTIONS} -DPCB=X9E ${SRCDIR} make -j${JOBS} libsimulator +cmake ${COMMON_OPTIONS} -DPCB=X10 ${SRCDIR} +make -j${JOBS} libsimulator + cmake ${COMMON_OPTIONS} -DPCB=X12S ${SRCDIR} make -j${JOBS} libsimulator diff -Nru opentx-companion22-2.2.0~ppa02~xenial/tools/build-companion-release.sh opentx-companion22-2.2.1~ppa01~xenial/tools/build-companion-release.sh --- opentx-companion22-2.2.0~ppa02~xenial/tools/build-companion-release.sh 2017-05-14 17:18:57.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/tools/build-companion-release.sh 2017-10-31 16:16:33.000000000 +0000 @@ -77,6 +77,9 @@ cmake ${COMMON_OPTIONS} -DPCB=X9E ${SRCDIR} make -j${JOBS} libsimulator +cmake ${COMMON_OPTIONS} -DPCB=X10 ${SRCDIR} +make -j${JOBS} libsimulator + cmake ${COMMON_OPTIONS} -DPCB=X12S ${SRCDIR} make -j${JOBS} libsimulator diff -Nru opentx-companion22-2.2.0~ppa02~xenial/tools/build-opentx.py opentx-companion22-2.2.1~ppa01~xenial/tools/build-opentx.py --- opentx-companion22-2.2.0~ppa02~xenial/tools/build-opentx.py 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/tools/build-opentx.py 2017-12-17 16:22:27.000000000 +0000 @@ -0,0 +1,110 @@ +#! /usr/bin/python +import cgitb +#cgitb.enable() + + +from pprint import pprint +from time import gmtime, strftime +from os.path import expanduser +import os +import os.path +import cgi +import sys +import re +import fcntl +import subprocess + +gitdir="~/cgibuild/opentx" +pidfile="~/cgibuild/opentxbuild.pid" +outdir="~/Sites/builds/" +builddir="~/cgibuild/" + +def main(): + print ("Content-Type: text/html\n") + + print (""" + + +

OpenTX 2.2 Companion build...

+ """) + + form = cgi.FieldStorage() + suffix = None + buildscript = "build-companion-release.sh" + if 'suffix' in form: + suffix = form.getfirst("suffix") + if not re.match("^[a-zA-Z0-9]*$", suffix): + status("Invalid suffix specified", True) + if suffix and not suffix.startswith("rc"): + buildscript = "build-companion-nightly.sh" + + if "branch" not in form or not re.match("^[a-z_\\-.A-Z0-9/]*$",form.getfirst("branch")): + status ("No branch specified or invalid branch\n", True) + + branch = form.getfirst("branch") + + status ("Branch %s - Suffix %s" %(branch, suffix)) + status ("Trying to get lock") + getlock_or_exit() + + logfile = open(os.path.join(expanduser(outdir),strftime("build-%Y-%m-%d %H:%M:%S.log", gmtime())),"w") + run_cmd(["git", "fetch"], gitdir, logfile) + run_cmd(["git", "checkout", "origin/%s" % branch], gitdir, logfile) + run_cmd(["git", "reset", "--hard"], gitdir, logfile) + + buildcmd = [os.path.join(expanduser(gitdir), "tools", buildscript), \ + "-j4", + expanduser(gitdir), \ + expanduser(outdir)] + if suffix: + buildcmd.append(suffix) + + + run_cmd(buildcmd, builddir, logfile) + status("Finished") + +def run_cmd(cmd, wd, logfile): + env = os.environ.copy() + env['PATH'] = env['PATH'] + ":/usr/local/bin/" + env['PYTHONPATH']="/usr/local/lib/python2.7/site-packages" + env['HOME']=expanduser("~") + + + status("Running '[%s]'" % ", ".join(cmd)) + p = subprocess.Popen(cmd, stdout=subprocess.PIPE, stderr=subprocess.STDOUT, cwd=expanduser(wd),env=env, bufsize=00) + + print("
\n")
+    sys.stdout.flush()
+
+    for line in p.stdout:
+        sys.stdout.write(line)
+        logfile.write(line)
+        if '\n' in line:
+            sys.stdout.flush()
+
+    print("
\n") + p.wait() + if(p.returncode != 0): + status( "failed with status %d" % p.returncode, True) + + +def getlock_or_exit(): + global fp + pid_file = expanduser(pidfile) + fp = open(pid_file, 'w') + try: + fcntl.lockf(fp, fcntl.LOCK_EX | fcntl.LOCK_NB) + fp.write("%s" % (os.getpid())) + except IOError as e: + # another instance is running + + status("could get lock, another instance running? %s " % str(e), True) + +def status(msg, exit=False): + print ("

%s - %s

\n" % (strftime("%Y-%m-%d %H:%M:%S", gmtime()),msg)) + if exit: + sys.exit(0) + +if __name__=="__main__": + main() + diff -Nru opentx-companion22-2.2.0~ppa02~xenial/tools/commit-tests.sh opentx-companion22-2.2.1~ppa01~xenial/tools/commit-tests.sh --- opentx-companion22-2.2.0~ppa02~xenial/tools/commit-tests.sh 2017-02-10 20:29:33.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/tools/commit-tests.sh 2017-12-17 16:22:27.000000000 +0000 @@ -8,7 +8,7 @@ : ${CORES:=2} # Default build treats warnings as errors, set -Wno-error to override, e.g.: commit-tests.sh -Wno-error : ${WERROR:=1} -# A board name to build for, or ALL +# A board name to build for, or ALL : ${FLAVOR:=ALL} for i in "$@" @@ -38,7 +38,7 @@ else SCRIPT=$(readlink -f "$0") fi -#export CMAKE_PREFIX_PATH=/opt/qt${QT_BASE} + if [[ ! -z ${GCC_ARM} ]] ; then export PATH=${GCC_ARM}:$PATH fi @@ -48,6 +48,10 @@ : ${COMMON_OPTIONS:="-DCMAKE_BUILD_TYPE=Debug -DTRACE_SIMPGMSPACE=NO -DVERBOSE_CMAKELISTS=YES -DCMAKE_RULE_MESSAGES=OFF -Wno-dev"} if (( $WERROR )); then COMMON_OPTIONS+=" -DWARNINGS_AS_ERRORS=YES"; fi +: ${EXTRA_OPTIONS:="$EXTRA_OPTIONS"} + +COMMON_OPTIONS+=${EXTRA_OPTIONS} + : ${TEST_OPTIONS:="--gtest_shuffle --gtest_repeat=5 --gtest_break_on_failure"} : ${FIRMARE_TARGET:="firmware-size"} @@ -58,80 +62,80 @@ if [[ " 9X AVR9X ALL " =~ " ${FLAVOR} " ]] ; then # OpenTX on 9X stock with FrSky telemetry rm -rf * - cmake ${COMMON_OPTIONS} -DPCB=9X -DHELI=YES -DTEMPLATES=YES -DTELEMETRY=FRSKY ${SRCDIR} + cmake ${COMMON_OPTIONS} -DPCB=9X -DHELI=YES -DTEMPLATES=YES -DGVARS=YES -DTELEMETRY=FRSKY ${SRCDIR} make -j${CORES} ${FIRMARE_TARGET} - make -j${CORES} simu + make -j${CORES} libsimulator make -j${CORES} gtests ; ./gtests ${TEST_OPTIONS} # OpenTX on 9X stock with Ardupilot telemetry rm -rf * - cmake ${COMMON_OPTIONS} -DPCB=9X -DHELI=YES -DTEMPLATES=YES -DTELEMETRY=ARDUPILOT ${SRCDIR} + cmake ${COMMON_OPTIONS} -DPCB=9X -DHELI=YES -DTEMPLATES=YES -DGVARS=YES -DTELEMETRY=ARDUPILOT ${SRCDIR} make -j${CORES} ${FIRMARE_TARGET} # OpenTX on 9X stock with JETI telemetry rm -rf * - cmake ${COMMON_OPTIONS} -DPCB=9X -DHELI=YES -DTEMPLATES=YES -DTELEMETRY=JETI ${SRCDIR} + cmake ${COMMON_OPTIONS} -DPCB=9X -DHELI=YES -DTEMPLATES=YES -DGVARS=YES -DTELEMETRY=JETI ${SRCDIR} make -j${CORES} ${FIRMARE_TARGET} fi if [[ " MEGA2560 AVR9X ALL " =~ " ${FLAVOR} " ]] ; then # OpenTX on Mega2560 rm -rf * - cmake ${COMMON_OPTIONS} -DPCB=MEGA2560 -DTEMPLATES=YES -DHELI=YES ${SRCDIR} + cmake ${COMMON_OPTIONS} -DPCB=MEGA2560 -DTEMPLATES=YES -DGVARS=YES -DHELI=YES ${SRCDIR} make -j${CORES} ${FIRMARE_TARGET} - make -j${CORES} simu + make -j${CORES} libsimulator make -j${CORES} gtests ; ./gtests ${TEST_OPTIONS} # OpenTX on Mega2560 with Mavlink telemetry rm -rf * - cmake ${COMMON_OPTIONS} -DPCB=MEGA2560 -DTELEMETRY=MAVLINK -DHELI=YES -DTEMPLATES=YES -DAUDIO=YES -DVOICE=YES ${SRCDIR} + cmake ${COMMON_OPTIONS} -DPCB=MEGA2560 -DTELEMETRY=MAVLINK -DHELI=YES -DTEMPLATES=YES -DAUDIO=YES -DVOICE=YES -DGVARS=YES ${SRCDIR} make -j${CORES} ${FIRMARE_TARGET} - make -j${CORES} simu + make -j${CORES} libsimulator make -j${CORES} gtests ; ./gtests ${TEST_OPTIONS} fi if [[ " GRUVIN9X AVR9X ALL " =~ " ${FLAVOR} " ]] ; then # OpenTX on gruvin9x board rm -rf * - cmake ${COMMON_OPTIONS} -DPCB=GRUVIN9X -DHELI=YES -DTEMPLATES=YES -DAUDIO=YES -DVOICE=YES ${SRCDIR} + cmake ${COMMON_OPTIONS} -DPCB=GRUVIN9X -DHELI=YES -DTEMPLATES=YES -DAUDIO=YES -DVOICE=YES -DGVARS=YES ${SRCDIR} make -j${CORES} ${FIRMARE_TARGET} - make -j${CORES} simu + make -j${CORES} libsimulator make -j${CORES} gtests ; ./gtests ${TEST_OPTIONS} fi if [[ " SKY9X ARM9X ALL " =~ " ${FLAVOR} " ]] ; then # OpenTX on Sky9x rm -rf * - cmake ${COMMON_OPTIONS} -DPCB=SKY9X -DHELI=YES ${SRCDIR} + cmake ${COMMON_OPTIONS} -DPCB=SKY9X -DHELI=YES DLUA=YES -DMULTIMODULE=YES -DTELEMETRY=FRSKY -DPPM_LIMITS_SYMETRICAL=YES -DVARIO=YES -DGAUGES=YES -DAUTOSWITCH=YES -DAUTOSOURCE=YES -DAUDIO=YES -DGPS=YES -DPPM_CENTER_ADJUSTABLE=YES -DFLIGHT_MODES=YES -DOVERRIDE_CHANNEL_FUNCTION=YES -DFRSKY_STICKS=YES -DGVARS=YES ${SRCDIR} make -j${CORES} ${FIRMARE_TARGET} - make -j${CORES} simu + make -j${CORES} libsimulator make -j${CORES} gtests ; ./gtests ${TEST_OPTIONS} fi if [[ " AR9X ARM9X ALL " =~ " ${FLAVOR} " ]] ; then # OpenTX on AR9X rm -rf * - cmake ${COMMON_OPTIONS} -DPCB=AR9X -DHELI=YES ${SRCDIR} + cmake ${COMMON_OPTIONS} -DPCB=AR9X -DHELI=YES -DGVARS=YES ${SRCDIR} make -j${CORES} ${FIRMARE_TARGET} - make -j${CORES} simu + make -j${CORES} libsimulator make -j${CORES} gtests ; ./gtests ${TEST_OPTIONS} fi if [[ " 9XRPRO ARM9X ALL " =~ " ${FLAVOR} " ]] ; then # OpenTX on Sky9x rm -rf * - cmake ${COMMON_OPTIONS} -DPCB=9XRPRO -DHELI=YES ${SRCDIR} + cmake ${COMMON_OPTIONS} -DPCB=9XRPRO -DHELI=YES -DGVARS=YES ${SRCDIR} make -j${CORES} ${FIRMARE_TARGET} - make -j${CORES} simu + make -j${CORES} libsimulator make -j${CORES} gtests ; ./gtests ${TEST_OPTIONS} fi if [[ " X7 ALL " =~ " ${FLAVOR} " ]] ; then # OpenTX on X7 rm -rf * - cmake ${COMMON_OPTIONS} -DPCB=X7 -DHELI=YES ${SRCDIR} + cmake ${COMMON_OPTIONS} -DPCB=X7 -DHELI=YES -DGVARS=YES ${SRCDIR} make -j${CORES} ${FIRMARE_TARGET} - make -j${CORES} simu + make -j${CORES} libsimulator make -j${CORES} gtests ; ./gtests ${TEST_OPTIONS} fi @@ -140,7 +144,7 @@ rm -rf * cmake ${COMMON_OPTIONS} -DPCB=X9D -DHELI=YES -DLUA=YES -DGVARS=YES ${SRCDIR} make -j${CORES} ${FIRMARE_TARGET} - make -j${CORES} simu + make -j${CORES} libsimulator make -j${CORES} gtests ; ./gtests ${TEST_OPTIONS} fi @@ -149,7 +153,7 @@ rm -rf * cmake ${COMMON_OPTIONS} -DPCB=X9D+ -DHELI=YES -DLUA=YES -DGVARS=YES ${SRCDIR} make -j${CORES} ${FIRMARE_TARGET} - make -j${CORES} simu + make -j${CORES} libsimulator make -j${CORES} gtests ; ./gtests ${TEST_OPTIONS} fi @@ -158,7 +162,7 @@ rm -rf * cmake ${COMMON_OPTIONS} -DPCB=X9E -DHELI=YES -DLUA=YES -DGVARS=YES -DPPM_UNIT=PERCENT_PREC1 ${SRCDIR} make -j${CORES} ${FIRMARE_TARGET} - make -j${CORES} simu + make -j${CORES} libsimulator make -j${CORES} gtests ; ./gtests ${TEST_OPTIONS} fi @@ -167,7 +171,7 @@ rm -rf * cmake ${COMMON_OPTIONS} -DPCB=X10 -DHELI=YES -DLUA=YES -DGVARS=YES ${SRCDIR} make -j${CORES} ${FIRMARE_TARGET} - make -j${CORES} simu + make -j${CORES} libsimulator make -j${CORES} gtests ; ./gtests ${TEST_OPTIONS} fi @@ -176,7 +180,7 @@ rm -rf * cmake ${COMMON_OPTIONS} -DPCB=X12S -DPCBREV=10 -DHELI=YES -DLUA=YES -DGVARS=YES ${SRCDIR} make -j${CORES} ${FIRMARE_TARGET} - make -j${CORES} simu + make -j${CORES} libsimulator make -j${CORES} gtests ; ./gtests ${TEST_OPTIONS} fi @@ -185,7 +189,7 @@ rm -rf * cmake ${COMMON_OPTIONS} -DPCB=X12S -DHELI=YES -DLUA=YES -DGVARS=YES ${SRCDIR} make -j${CORES} ${FIRMARE_TARGET} - make -j${CORES} simu + make -j${CORES} libsimulator make -j${CORES} gtests ; ./gtests ${TEST_OPTIONS} fi diff -Nru opentx-companion22-2.2.0~ppa02~xenial/tools/nightly22/build-nightly.sh opentx-companion22-2.2.1~ppa01~xenial/tools/nightly22/build-nightly.sh --- opentx-companion22-2.2.0~ppa02~xenial/tools/nightly22/build-nightly.sh 2017-05-31 19:50:06.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/tools/nightly22/build-nightly.sh 2017-10-31 16:16:33.000000000 +0000 @@ -6,7 +6,7 @@ docker=nightly22 workdir=/home/opentx/nightly22 output=/var/www/html/2.2/nightlies -version=2.2.0 +version=2.2.1 # Incrementnightly index index=`cat index.txt` @@ -55,7 +55,7 @@ # Update stamps cp -f ${workdir}/binaries/stamp-opentx.txt ${output}/firmware -echo "#define VERSION "'"2.2.0'$suffix'"' > ${output}/companion/companion-windows.stamp +echo "#define VERSION \"${version}${suffix}\"" > ${output}/companion/companion-windows.stamp cp -f ${output}/companion/companion-windows.stamp ${output}/companion/companion-linux.stamp cp -f ${output}/companion/companion-windows.stamp ${output}/companion/companion-macosx.stamp diff -Nru opentx-companion22-2.2.0~ppa02~xenial/tools/nightly22/tts.py opentx-companion22-2.2.1~ppa01~xenial/tools/nightly22/tts.py --- opentx-companion22-2.2.0~ppa02~xenial/tools/nightly22/tts.py 2017-05-31 19:50:06.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/tools/nightly22/tts.py 2017-10-31 16:16:44.000000000 +0000 @@ -37,7 +37,9 @@ output = "output.mp3" command = 'gtts-cli -l %s -o %s "%s"' % (voice[:2], output, str) os.system(command.encode('utf-8')) - command = "sox %s -r 32000 %s" % (output, filename) + command = "sox %s -r 32000 %s tempo 1.2" % (output, filename) + os.system(command.encode('utf-8')) + command = "rm -f output.mp3" os.system(command.encode('utf-8')) ################################################################ @@ -84,7 +86,7 @@ directory = "pt" voice = "pt-PT" - + else: print("which language?") exit() diff -Nru opentx-companion22-2.2.0~ppa02~xenial/tools/rc22/build-rc.sh opentx-companion22-2.2.1~ppa01~xenial/tools/rc22/build-rc.sh --- opentx-companion22-2.2.0~ppa02~xenial/tools/rc22/build-rc.sh 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/tools/rc22/build-rc.sh 2017-12-17 16:22:27.000000000 +0000 @@ -0,0 +1,71 @@ +#!/bin/bash + +set -e + +branch=2.2 +docker=rc22 +workdir=/home/opentx/rc22 +output=/var/www/html/2.2/rc +version=2.2.1 + +# Incrementnightly index +index=`cat index.txt` +index=`expr $index + 1` +suffix="RC$index" + +cd ${workdir} + +# Create on-demand build environment +cp code/radio/util/Dockerfile . +docker build -t new-${docker} --build-arg OPENTX_VERSION_SUFFIX=${suffix} . +set +e +docker rmi -f ${docker} +set -e +docker tag new-${docker} ${docker} +docker rmi -f new-${docker} + +# Call sdcard generation +code/tools/rc22/build-sdcard.sh + +# Build Linux companion +docker run -dit --name companion -v /home/opentx/${docker}:/opentx ${docker} +docker exec companion sh -c "mkdir -p build && cd build && cmake /opentx/code && cp radio/src/stamp.h /opentx/binaries/stamp-opentx.txt" +docker exec companion rm -rf build +if [ ! -f ${output}/companion/linux/companion22_${version}${suffix}_amd64.deb ]; then + docker exec companion /opentx/code/tools/build-companion-release.sh /opentx/code /opentx/binaries/ + docker exec companion sh -c "cp /build/radio/src/lua/*.txt /opentx/binaries" + cp -f binaries/*.deb ${output}/companion/linux/companion22_${version}${suffix}_amd64.deb + cp -f binaries/lua_fields_*.txt ${output}/firmware +fi +docker stop companion +docker rm companion + +# Request companion compilation on Windows +if [ ! -f ${output}/companion/windows/companion-windows-${version}${suffix}.exe ]; then + cd ${output}/companion/windows + wget -qO- http://winbox.open-tx.org/companion-builds/compile22.php?branch=$branch\&suffix=${suffix} + wget -O companion-windows-${version}${suffix}.exe http://winbox.open-tx.org/companion-builds/companion-windows-${version}${suffix}.exe + chmod -Rf g+w companion-windows-${version}${suffix}.exe +fi + +# Request companion compilation on Mac OS X +if [ ! -f ${output}/companion/macosx/opentx-companion-${version}${suffix}.dmg ]; then + cd ${output}/companion/macosx + wget -qO- http://opentx.blinkt.de:8080/~opentx/build-opentx.py?branch=${branch}\&suffix=${suffix} + wget -O opentx-companion-${version}${suffix}.dmg http://opentx.blinkt.de:8080/~opentx/builds/opentx-companion-${version}${suffix}.dmg + chmod -Rf g+w opentx-companion-${version}${suffix}.dmg +fi + +# Update stamps +cp -f $workdir/binaries/stamp-opentx.txt ${output}/firmware +echo "#define VERSION \"${version}${suffix}\"" > ${output}/companion/companion-windows.stamp +cp -f ${output}/companion/companion-windows.stamp ${output}/companion/companion-macosx.stamp +cp -f ${output}/companion/companion-windows.stamp ${output}/companion/companion-linux.stamp + + +# Clean binaries It will be hosting built on demand firmware +rm -rf $workdir/binaries/* +rm -rf $workdir/binaries/.lock + +# RC is considered as valid ony if we get to that point +echo $index > ${workdir}/index.txt diff -Nru opentx-companion22-2.2.0~ppa02~xenial/tools/rc22/build-sdcard.sh opentx-companion22-2.2.1~ppa01~xenial/tools/rc22/build-sdcard.sh --- opentx-companion22-2.2.0~ppa02~xenial/tools/rc22/build-sdcard.sh 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/tools/rc22/build-sdcard.sh 2017-12-17 16:22:27.000000000 +0000 @@ -0,0 +1,59 @@ +#!/bin/bash + +set -e + +branch=2.2 +workdir=/home/opentx/rc22 +output=/media/HDD/www2/sdcard/rc + +# Handle opentx.sdcard.version +sdcard_version="2.2V"$(grep 'set(SDCARD_REVISION' ${workdir}/code/CMakeLists.txt | grep -o '".*"' | sed 's/"//g') +echo ${sdcard_version} > ${workdir}/code/radio/sdcard/horus/opentx.sdcard.version +echo ${sdcard_version} > ${workdir}/code/radio/sdcard/taranis-x9/opentx.sdcard.version +echo ${sdcard_version} > ${workdir}/code/radio/sdcard/taranis-x7/opentx.sdcard.version + +if cmp --silent ${workdir}/code/radio/sdcard/horus/opentx.sdcard.version ${workdir}/opentx.sdcard.version +then + exit +else + cp -r ${workdir}/code/radio/sdcard/horus/opentx.sdcard.version ${workdir} + cd ${workdir} + + # Copy git sdcard data + rm -Rf ${workdir}/sdcard + cp -r ${workdir}/code/radio/sdcard . + + # Get images for Horus + mkdir -p ${workdir}/sdcard/horus/IMAGES + imgdir=/home/opentx/horus-bitmaps + if [ "$(ls -A $imgdir)" ]; then + cp /$imgdir/* ${workdir}/sdcard/horus/IMAGES/ + fi + + # Get images for Taranis x9 + mkdir -p ${workdir}/sdcard/taranis-x9/IMAGES + imgdir=/home/opentx/x9-bitmaps + if [ "$(ls -A $imgdir)" ]; then + cp $imgdir/* ${workdir}/sdcard/taranis-x9/IMAGES/ + fi + + # Request sound pack generation + python3 -B ${workdir}/code/tools/rc22/tts.py en csv files + python3 -B ${workdir}/code/tools/rc22/tts.py fr csv files + python3 -B ${workdir}/code/tools/rc22/tts.py es csv files + python3 -B ${workdir}/code/tools/rc22/tts.py it csv files + python3 -B ${workdir}/code/tools/rc22/tts.py de csv files + python3 -B ${workdir}/code/tools/nightly22/tts.py cz csv files + python3 -B ${workdir}/code/tools/nightly22/tts.py pt csv files + + # Create sdcards.zips for supported platforms + mv /tmp/SOUNDS ${workdir}/sdcard/horus/ + mkdir ${workdir}/sdcard/taranis-x9/SOUNDS + mkdir ${workdir}/sdcard/taranis-x7/SOUNDS + cp -r ${workdir}/sdcard/horus/SOUNDS ${workdir}/sdcard/taranis-x9/ + cp -r ${workdir}/sdcard/horus/SOUNDS ${workdir}/sdcard/taranis-x7/ + cd ${workdir}/sdcard/horus && zip -r ${output}/opentx-x12s/sdcard-horus-${sdcard_version}.zip * + cd ${workdir}/sdcard/taranis-x9 && zip -r ${output}/opentx-x9d/sdcard-taranis-x9-${sdcard_version}.zip * + cd ${workdir}/sdcard/taranis-x7 && zip -r ${output}/opentx-x7/sdcard-taranis-x7-${sdcard_version}.zip * + rm -Rf ${workdir}/sdcard +fi diff -Nru opentx-companion22-2.2.0~ppa02~xenial/tools/rc22/tts_common.py opentx-companion22-2.2.1~ppa01~xenial/tools/rc22/tts_common.py --- opentx-companion22-2.2.0~ppa02~xenial/tools/rc22/tts_common.py 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/tools/rc22/tts_common.py 2017-12-17 16:22:27.000000000 +0000 @@ -0,0 +1,14 @@ +NO_ALTERNATE = 1024 +PROMPT_CUSTOM_BASE = 256 +PROMPT_SYSTEM_BASE = 0 +board = "taranis" + +import sys + +def filename(idx, alternate=0): + ext = ".wav" + if isinstance(idx, int): + result = "%04d%s" % (idx, ext) + elif board in ('sky9x', 'taranis'): + result = idx + ext + return result diff -Nru opentx-companion22-2.2.0~ppa02~xenial/tools/rc22/tts.py opentx-companion22-2.2.1~ppa01~xenial/tools/rc22/tts.py --- opentx-companion22-2.2.0~ppa02~xenial/tools/rc22/tts.py 1970-01-01 00:00:00.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/tools/rc22/tts.py 2017-12-17 16:22:27.000000000 +0000 @@ -0,0 +1,126 @@ +#!/usr/bin/env python +# -*- coding: utf-8 -*- + + +# This script is a modified version to support Linux TTS fiel genration using PicoTTS + +# Sound pack maintainers (incomplete list) by language alphabetical order +# Czech : Martin Hotar +# French : Bertrand Songis & André Bernet +# English : Rob Thompson & Martin Hotar +# German : Romolo Manfredini (Some corrections by Peer) +# Italian : Romolo Manfredini +# Portuguese : Romolo Manfredini +# Spanish : Romolo Manfredini (With the help of Jose Moreno) + +# from __future__ import print_function + +import os +import sys +import subprocess +import zipfile +from tts_common import * +board = "taranis" + +SOURCE_DIRECTORY = os.path.dirname(os.path.realpath(__file__)) +lib_path = os.path.abspath(os.path.join(SOURCE_DIRECTORY, '..', '..', 'radio', 'util')) +sys.path.append(lib_path) + +def generate(str, filename): + if 0: + output = "output.wav" + command = 'pico2wave -l=%s -w=%s "%s"' % (voice, output, str) + os.system(command.encode('utf-8')) + command = "sox %s -r 32000 %s reverse silence 1 0.1 0.1%% reverse" % (output, filename) + os.system(command.encode('utf-8')) + else: + output = "output.mp3" + command = 'gtts-cli -l %s -o %s "%s"' % (voice[:2], output, str) + os.system(command.encode('utf-8')) + command = "sox %s -r 32000 %s tempo 1.2" % (output, filename) + os.system(command.encode('utf-8')) + command = "rm -f output.mp3" + os.system(command.encode('utf-8')) + +################################################################ + +if __name__ == "__main__": + if "en" in sys.argv: + from tts_en import systemSounds, sounds + + directory = "en" + voice = "en-US" + + elif "fr" in sys.argv: + from tts_fr import systemSounds, sounds + + directory = "fr" + voice = "fr-FR" + + elif "it" in sys.argv: + from tts_it import systemSounds, sounds + + directory = "it" + voice = "it-IT" + + elif "de" in sys.argv: + from tts_de import systemSounds, sounds + + directory = "de" + voice = "de-DE" + + elif "es" in sys.argv: + from tts_es import systemSounds, sounds + + directory = "es" + voice = "es-ES" + + elif "cz" in sys.argv: + from tts_cz import systemSounds, sounds + + directory = "cz" + voice = "cs-CZ" + + elif "pt" in sys.argv: + from tts_pt import systemSounds, sounds + + directory = "pt" + voice = "pt-PT" + + else: + print("which language?") + exit() + + if "csv" in sys.argv: + path = "/tmp/SOUNDS/" + directory + "/SYSTEM/" + if not os.path.exists(path): + os.makedirs(path) + os.chdir(path) + with open("%s-%s.csv" % (voice, board), "wb") as csvFile: + for s, f in systemSounds: + if s and f: + l = u"" + if board in ("sky9x", "taranis"): + l += u"SOUNDS/%s/SYSTEM;" % directory + l += f + u";" + s + u"\n" + csvFile.write(l.encode("utf-8")) + for s, f in sounds: + if s and f: + l = u"" + if board in ("sky9x", "taranis"): + l += u"SOUNDS/%s;" % directory + l += f + u";" + s + u"\n" + csvFile.write(l.encode("utf-8")) + + if "files" in sys.argv: + path = "/tmp/SOUNDS/" + directory + "/SYSTEM/" + if not os.path.exists(path): + os.makedirs(path) + os.chdir(path) + for s, f in systemSounds: + if s and f: + generate(s, f) + os.chdir("..") + for s, f in sounds: + if s and f: + generate(s, f) diff -Nru opentx-companion22-2.2.0~ppa02~xenial/tools/release22/build-release.sh opentx-companion22-2.2.1~ppa01~xenial/tools/release22/build-release.sh --- opentx-companion22-2.2.0~ppa02~xenial/tools/release22/build-release.sh 2017-05-14 17:18:57.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/tools/release22/build-release.sh 2017-12-17 16:22:27.000000000 +0000 @@ -6,7 +6,7 @@ docker=release22 workdir=/home/opentx/release22 output=/var/www/html/2.2 -version=2.2.0 +version=2.2.1 cd ${workdir} diff -Nru opentx-companion22-2.2.0~ppa02~xenial/tools/release22/build-sdcard.sh opentx-companion22-2.2.1~ppa01~xenial/tools/release22/build-sdcard.sh --- opentx-companion22-2.2.0~ppa02~xenial/tools/release22/build-sdcard.sh 2017-05-14 17:18:57.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/tools/release22/build-sdcard.sh 2017-10-31 16:16:33.000000000 +0000 @@ -27,6 +27,10 @@ mkdir -p ${workdir}/sdcard/horus/IMAGES cp /home/opentx/horus-bitmaps/* ${workdir}/sdcard/horus/IMAGES/ + # Get images for Taranis x9 + mkdir -p ${workdir}/sdcard/taranis-x9/IMAGES + cp /home/opentx/x9-bitmaps/* ${workdir}/sdcard/taranis-x9/IMAGES/ + # Request sound pack generation python3 -B ${workdir}/code/tools/release22/tts.py en csv files python3 -B ${workdir}/code/tools/release22/tts.py fr csv files diff -Nru opentx-companion22-2.2.0~ppa02~xenial/tools/release22/tts.py opentx-companion22-2.2.1~ppa01~xenial/tools/release22/tts.py --- opentx-companion22-2.2.0~ppa02~xenial/tools/release22/tts.py 2017-05-31 19:50:06.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/tools/release22/tts.py 2017-10-31 16:16:44.000000000 +0000 @@ -37,7 +37,9 @@ output = "output.mp3" command = 'gtts-cli -l %s -o %s "%s"' % (voice[:2], output, str) os.system(command.encode('utf-8')) - command = "sox %s -r 32000 %s" % (output, filename) + command = "sox %s -r 32000 %s tempo 1.2" % (output, filename) + os.system(command.encode('utf-8')) + command = "rm -f output.mp3" os.system(command.encode('utf-8')) ################################################################ diff -Nru opentx-companion22-2.2.0~ppa02~xenial/.travis.yml opentx-companion22-2.2.1~ppa01~xenial/.travis.yml --- opentx-companion22-2.2.0~ppa02~xenial/.travis.yml 2017-04-19 17:34:22.000000000 +0000 +++ opentx-companion22-2.2.1~ppa01~xenial/.travis.yml 2017-12-17 16:22:27.000000000 +0000 @@ -18,6 +18,7 @@ # - QT_BASE=57 #- GCC_ARM=/opt/gcc-arm-none-eabi/bin - AVR_FLAVORS="AVR9X 9X GRUVIN9X MEGA2560" + - PYTHONPATH=${PYTHONPATH}:/usr/lib/python3/dist-packages matrix: # # ALL will build every individual board & DEFAULT, sequentially. @@ -72,5 +73,21 @@ fi - sudo apt-get install --yes --force-yes -qq qt${QT_BASE}base qt${QT_BASE}multimedia qt${QT_BASE}svg qt${QT_BASE}tools; source /opt/qt${QT_BASE}/bin/qt${QT_BASE}-env.sh +addons: + sonarcloud: + organization: "opentx-github" + token: + secure: "BuQrGRijNpL2V/IQNcOxvjChj8PScfCdiv403EE73Nqb4+sB8YL92Fnzrnw9bC8wF7BVSDJVpYF0gbdaTzuCmaeZfM8NJK0TOJAbH6+B8bhIrU/V1SBuVjHQnndV/wysieruKnK/KxYJZqItgSlnPo+PmiFxtXJNlas0Kstb2O4=" + # github_token: + # secure: "Qkmp4VrQJtKgZ/pz65SNnCDiF4slgFfQS/3whyLXLcDbFb1Hv1oj7Hqz9EVDUSO2eEhgQGaOKkRc0CfAAOBwW6OvhE0xh7P1CJEjzOp6+3gI/LyZUNsqa+awVRZTsfm1YZaOPaPWJ7cI0uz3/OoSUeIecs4PDWPrQMGRlsrq7Q8=" + branches: + - "2.2" + script: - - ./tools/commit-tests.sh + - build-wrapper-linux-x86-64 --out-dir bw_output ./tools/commit-tests.sh + - sonar-scanner + +cache: + directories: + - '$HOME/.sonar/cache' +