Compare commits
74 Commits
2.2.0-RC18
...
2.2.0
| Author | SHA1 | Date | |
|---|---|---|---|
| 85863358fb | |||
| b397af1bac | |||
| 0906bdc6d7 | |||
| 77925f6abc | |||
| 0a0893e6cc | |||
| 3d17023bc9 | |||
| fd16151850 | |||
| 2ae0472f76 | |||
| cd23fedb56 | |||
| 1cb0156cd0 | |||
| 4880c029b7 | |||
| c79994d812 | |||
| f462af1b0e | |||
| 8729bbc41b | |||
| 0fc1681d5c | |||
| 69576cb17d | |||
| 1a85956dcb | |||
| 01150497bb | |||
| 0ed7f5a5ad | |||
| ce83cf00e0 | |||
| 8eea072cd1 | |||
| 4d23292ad3 | |||
| 618832974e | |||
| c80fbf2de7 | |||
| 5b69ceff0d | |||
| 3cc3687dcb | |||
| eb7c73668f | |||
| d35d3b5e22 | |||
| 935518f6dd | |||
| 20dcee3a5c | |||
| 5825a2ec2c | |||
| 355f4b5f92 | |||
| 9437d98df9 | |||
| 7a8ca1c675 | |||
| 79d9359e56 | |||
| 006166a25c | |||
| 33cc0861a6 | |||
| d48ab63497 | |||
| bd62281144 | |||
| 50397d0052 | |||
| 460e6aab96 | |||
| 95b0a21cfc | |||
| f7b6d95910 | |||
| 6e0bec9db4 | |||
| 83132ef041 | |||
| c1586b72bb | |||
| ca25696d1a | |||
| 11579d9118 | |||
| 32714fb841 | |||
| 2bc2030f86 | |||
| 93dbdf8680 | |||
| 301e33a271 | |||
| 53bb8bc6c3 | |||
| e2502772cb | |||
| 24de312a30 | |||
| efe53eb034 | |||
| 96ccb4cb3f | |||
| 3f06037e1b | |||
| 38d8f6a326 | |||
| 2bec60517a | |||
| d3b8133ee2 | |||
| 4b2b5a9d37 | |||
| 6edc3b61ff | |||
| f525b1762b | |||
| 4f5f241669 | |||
| 0b25332171 | |||
| 054c87c91e | |||
| e053abfc3e | |||
| 6abd36d628 | |||
| 582546f8ed | |||
| c1e7235375 | |||
| 975023bdc7 | |||
| b8e0f26a22 | |||
| 22217e8e22 |
+4
-1
@@ -6,7 +6,7 @@ set(VERSION_REVISION "0")
|
||||
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 "0009")
|
||||
set(SDCARD_REVISION "0010")
|
||||
set(SDCARD_VERSION ${VERSION_MAJOR}.${VERSION_MINOR}V${SDCARD_REVISION})
|
||||
|
||||
cmake_minimum_required(VERSION 2.8)
|
||||
@@ -133,6 +133,9 @@ if(Qt5Core_FOUND OR FOX_FOUND)
|
||||
find_package("SDL")
|
||||
if(SDL_FOUND)
|
||||
message(STATUS "SDL Lib: ${SDL_LIBRARY}; Headers: ${SDL_INCLUDE_DIR}; Version: ${SDL_VERSION_STRING}")
|
||||
if (NOT ${SDL_VERSION_STRING} VERSION_LESS "2.0")
|
||||
message(FATAL_ERROR "OpenTX requires SDL 1.x, not 2.x")
|
||||
endif()
|
||||
else()
|
||||
message(STATUS "SDL not found! Simulator audio, and joystick inputs, will not work.")
|
||||
endif()
|
||||
|
||||
+1203
File diff suppressed because it is too large
Load Diff
-1183
File diff suppressed because it is too large
Load Diff
@@ -10,7 +10,6 @@ The ongoing development on 2.2.x is done in this branch.
|
||||
Refer to the [OpenTX wiki](https://github.com/opentx/opentx/wiki) for information about setting up the tool chains for building OpenTX and OpenTX Companion as well as other development related issues.
|
||||
|
||||
Useful links:
|
||||
* OpenTX Blog http://blog.open-tx.org/
|
||||
* OpenTX Main Site http://www.open-tx.org/
|
||||
* OpenTx University http://open-txu.org/
|
||||
* OpenTX User Manual https://www.gitbook.com/book/opentx/opentx-taranis-manual/details
|
||||
|
||||
@@ -218,7 +218,7 @@ set(companion_SRCS
|
||||
burnconfigdialog.cpp
|
||||
multimodelprinter.cpp
|
||||
comparedialog.cpp
|
||||
contributorsdialog.cpp
|
||||
creditsdialog.cpp
|
||||
releasenotesdialog.cpp
|
||||
releasenotesfirmwaredialog.cpp
|
||||
customizesplashdialog.cpp
|
||||
@@ -252,7 +252,7 @@ set(companion_MOC_HDRS
|
||||
printdialog.h
|
||||
fusesdialog.h
|
||||
logsdialog.h
|
||||
contributorsdialog.h
|
||||
creditsdialog.h
|
||||
releasenotesdialog.h
|
||||
releasenotesfirmwaredialog.h
|
||||
customizesplashdialog.h
|
||||
|
||||
@@ -3,7 +3,6 @@
|
||||
<file>images/customize.png</file>
|
||||
<file>icon.png</file>
|
||||
<file>../../CREDITS.txt</file>
|
||||
<file>../../DONATIONS.txt</file>
|
||||
<file>../releasenotes.txt</file>
|
||||
<file>images/screenshot.png</file>
|
||||
<file>images/splash.png</file>
|
||||
|
||||
+16
-14
@@ -21,6 +21,8 @@
|
||||
#ifndef _CONSTANTS_H_
|
||||
#define _CONSTANTS_H_
|
||||
|
||||
#include <QCoreApplication>
|
||||
|
||||
#define CPN_MAX_MODELS 60
|
||||
#define CPN_MAX_TIMERS 3
|
||||
#define CPN_MAX_FLIGHT_MODES 9
|
||||
@@ -47,23 +49,23 @@
|
||||
#define CPN_MAX_MOUSE_ANALOGS 2
|
||||
#define CPN_MAX_ANALOGS (CPN_MAX_STICKS + CPN_MAX_POTS + CPN_MAX_MOUSE_ANALOGS)
|
||||
|
||||
#define CPN_STR_FILES QT_TRANSLATE_NOOP("CompanionMacros", "files")
|
||||
#define CPN_STR_RAD_MOD_SETTINGS QT_TRANSLATE_NOOP("CompanionMacros", "Radio and Models settings")
|
||||
#define HEX_FILES_FILTER "HEX " CPN_STR_FILES " (*.hex);;"
|
||||
#define BIN_FILES_FILTER "BIN " CPN_STR_FILES " (*.bin);;"
|
||||
#define DFU_FILES_FILTER "DFU " CPN_STR_FILES " (*.dfu);;"
|
||||
#define EEPE_FILES_FILTER "EEPE " CPN_STR_FILES " (*.eepe);;"
|
||||
#define OTX_FILES_FILTER "OpenTX " CPN_STR_FILES " (*.otx);;"
|
||||
#define EEPROM_FILES_FILTER CPN_STR_RAD_MOD_SETTINGS " " CPN_STR_FILES " (*.otx *.eepe *.bin *.hex);;" OTX_FILES_FILTER EEPE_FILES_FILTER BIN_FILES_FILTER HEX_FILES_FILTER
|
||||
#define FLASH_FILES_FILTER "FLASH " CPN_STR_FILES " (*.bin *.hex *.dfu);;" BIN_FILES_FILTER HEX_FILES_FILTER DFU_FILES_FILTER
|
||||
#define EXTERNAL_EEPROM_FILES_FILTER "EEPROM " CPN_STR_FILES " (*.bin *.hex);;" BIN_FILES_FILTER HEX_FILES_FILTER
|
||||
#define CPN_STR_FILES QCoreApplication::translate("Companion", "files")
|
||||
#define CPN_STR_RAD_MOD_SETTINGS QCoreApplication::translate("Companion", "Radio and Models settings")
|
||||
#define HEX_FILES_FILTER "HEX " % CPN_STR_FILES % " (*.hex);;"
|
||||
#define BIN_FILES_FILTER "BIN " % CPN_STR_FILES % " (*.bin);;"
|
||||
#define DFU_FILES_FILTER "DFU " % CPN_STR_FILES % " (*.dfu);;"
|
||||
#define EEPE_FILES_FILTER "EEPE " % CPN_STR_FILES % " (*.eepe);;"
|
||||
#define OTX_FILES_FILTER "OpenTX " % CPN_STR_FILES % " (*.otx);;"
|
||||
#define EEPROM_FILES_FILTER CPN_STR_RAD_MOD_SETTINGS % " " % CPN_STR_FILES % " (*.otx *.eepe *.bin *.hex);;" % OTX_FILES_FILTER % EEPE_FILES_FILTER % BIN_FILES_FILTER % HEX_FILES_FILTER
|
||||
#define FLASH_FILES_FILTER "FLASH " % CPN_STR_FILES % " (*.bin *.hex *.dfu);;" % BIN_FILES_FILTER % HEX_FILES_FILTER % DFU_FILES_FILTER
|
||||
#define EXTERNAL_EEPROM_FILES_FILTER "EEPROM " % CPN_STR_FILES % " (*.bin *.hex);;" % BIN_FILES_FILTER % HEX_FILES_FILTER
|
||||
#define ER9X_EEPROM_FILE_TYPE "ER9X_EEPROM_FILE"
|
||||
#define EEPE_EEPROM_FILE_HEADER "EEPE EEPROM FILE"
|
||||
#define EEPE_MODEL_FILE_HEADER "EEPE MODEL FILE"
|
||||
|
||||
#define CPN_STR_SW_INDICATOR_UP QT_TRANSLATE_NOOP("RawSwitch", "\xE2\x86\x91") // Switch up position indicator: Up arrow, or similar.
|
||||
#define CPN_STR_SW_INDICATOR_DN QT_TRANSLATE_NOOP("RawSwitch", "\xE2\x86\x93") // Switch down position indicator: Down arrow, or similar.
|
||||
#define CPN_STR_SW_INDICATOR_NEUT QT_TRANSLATE_NOOP("RawSwitch", "-") // Switch neutral (middle) position indicator.
|
||||
#define CPN_STR_SW_INDICATOR_REV QT_TRANSLATE_NOOP("RawSwitch", "!") // Switch reversed logic (NOT) indicator.
|
||||
#define CPN_STR_SW_INDICATOR_UP QCoreApplication::translate("RawSwitch", "\xE2\x86\x91") // Switch up position indicator: Up arrow, or similar.
|
||||
#define CPN_STR_SW_INDICATOR_DN QCoreApplication::translate("RawSwitch", "\xE2\x86\x93") // Switch down position indicator: Down arrow, or similar.
|
||||
#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.
|
||||
|
||||
#endif // _CONSTANTS_H_
|
||||
|
||||
@@ -18,12 +18,12 @@
|
||||
* GNU General Public License for more details.
|
||||
*/
|
||||
|
||||
#include "contributorsdialog.h"
|
||||
#include "creditsdialog.h"
|
||||
#include "ui_htmldialog.h"
|
||||
#include "helpers.h"
|
||||
#include <QFile>
|
||||
|
||||
ContributorsDialog::ContributorsDialog(QWidget * parent):
|
||||
CreditsDialog::CreditsDialog(QWidget * parent):
|
||||
QDialog(parent),
|
||||
ui(new Ui::HtmlDialog)
|
||||
{
|
||||
@@ -42,42 +42,8 @@ ContributorsDialog::ContributorsDialog(QWidget * parent):
|
||||
"</head>"
|
||||
"<body class=\"normal\">";
|
||||
|
||||
QFile credits(":/CREDITS.txt");
|
||||
if (credits.open(QIODevice::ReadOnly | QIODevice::Text)) {
|
||||
QStringList names;
|
||||
while (!credits.atEnd()) {
|
||||
QByteArray line = credits.readLine();
|
||||
if (line.trimmed() == "")
|
||||
break;
|
||||
names.append(line.trimmed());
|
||||
}
|
||||
str.append(formatTable(tr("Main Developers"), names, 3));
|
||||
|
||||
names.clear();
|
||||
while (!credits.atEnd()) {
|
||||
QByteArray line = credits.readLine();
|
||||
names.append(line.trimmed());
|
||||
}
|
||||
str.append(formatTable(tr("Other contributors"), names, 3));
|
||||
}
|
||||
|
||||
QFile donations(":/DONATIONS.txt");
|
||||
if (donations.open(QIODevice::ReadOnly | QIODevice::Text)) {
|
||||
QStringList names;
|
||||
while (!donations.atEnd()) {
|
||||
QByteArray line = donations.readLine();
|
||||
if (line.trimmed() == "")
|
||||
break;
|
||||
names.append(line.trimmed());
|
||||
}
|
||||
str.append(formatTable(tr("Companies and projects who have donated to OpenTX"), names, 3));
|
||||
|
||||
names.clear();
|
||||
while (!donations.atEnd()) {
|
||||
QByteArray line = donations.readLine();
|
||||
names.append(line);
|
||||
}
|
||||
str.append(formatTable(tr("People who have donated to OpenTX"), names, 6));
|
||||
foreach(CreditsSection section, readCredits()) {
|
||||
str.append(formatTable(sectionTitle(section.title), section.names, 3));
|
||||
}
|
||||
|
||||
str.append("<table><tr><td class=\"normal\"> </td></tr>" \
|
||||
@@ -87,9 +53,9 @@ ContributorsDialog::ContributorsDialog(QWidget * parent):
|
||||
#if 0
|
||||
QFile blacklist(":/BLACKLIST.txt");
|
||||
if (blacklist.open(QIODevice::ReadOnly | QIODevice::Text)) {
|
||||
QStringList names;
|
||||
names << blacklist.readAll();
|
||||
str.append(formatTable(tr("OpenTX Blacklist"), names, 1));
|
||||
QStringList names;
|
||||
names << blacklist.readAll();
|
||||
str.append(formatTable(tr("OpenTX Blacklist"), names, 1));
|
||||
}
|
||||
#endif
|
||||
|
||||
@@ -99,12 +65,45 @@ ContributorsDialog::ContributorsDialog(QWidget * parent):
|
||||
ui->textEditor->setOpenExternalLinks(true);
|
||||
}
|
||||
|
||||
ContributorsDialog::~ContributorsDialog()
|
||||
CreditsDialog::~CreditsDialog()
|
||||
{
|
||||
delete ui;
|
||||
}
|
||||
|
||||
QString ContributorsDialog::formatTable(const QString & title, const QStringList & names, int columns)
|
||||
QList<CreditsDialog::CreditsSection> CreditsDialog::readCredits()
|
||||
{
|
||||
QFile credits(":/CREDITS.txt");
|
||||
QList<CreditsSection> result;
|
||||
if (credits.open(QIODevice::ReadOnly | QIODevice::Text)) {
|
||||
while (!credits.atEnd()) {
|
||||
QByteArray line = credits.readLine().trimmed();
|
||||
if (line.size() >= 2) {
|
||||
if (line.startsWith("[") && line.endsWith("]")) {
|
||||
result.push_back(CreditsSection(line.mid(1, line.size() - 2)));
|
||||
} else {
|
||||
result.back().addName(line);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
QString CreditsDialog::sectionTitle(const QString & title)
|
||||
{
|
||||
if (title == "Main developers")
|
||||
return tr("Main developers");
|
||||
else if (title == "Translators")
|
||||
return tr("Translators");
|
||||
else if (title == "Companies and projects who have donated to OpenTX")
|
||||
return tr("Companies and projects who have donated to OpenTX");
|
||||
else if (title == "People who have donated to OpenTX")
|
||||
return tr("People who have donated to OpenTX");
|
||||
else
|
||||
return tr("Other contributors");
|
||||
}
|
||||
|
||||
QString CreditsDialog::formatTable(const QString & title, const QStringList & names, int columns)
|
||||
{
|
||||
const float cwidth = 100.0 / columns;
|
||||
QString str = "<table width=\"100%\" border=0 cellspacing=0 cellpadding=2>" \
|
||||
@@ -18,8 +18,8 @@
|
||||
* GNU General Public License for more details.
|
||||
*/
|
||||
|
||||
#ifndef _CONTRIBUTORSDIALOG_H_
|
||||
#define _CONTRIBUTORSDIALOG_H_
|
||||
#ifndef _CREDITSDIALOG_H_
|
||||
#define _CREDITSDIALOG_H_
|
||||
|
||||
#include <QDialog>
|
||||
|
||||
@@ -27,17 +27,36 @@ namespace Ui {
|
||||
class HtmlDialog;
|
||||
}
|
||||
|
||||
class ContributorsDialog : public QDialog
|
||||
class CreditsDialog : public QDialog
|
||||
{
|
||||
Q_OBJECT
|
||||
|
||||
class CreditsSection
|
||||
{
|
||||
public:
|
||||
CreditsSection(const QString & title):
|
||||
title(title)
|
||||
{
|
||||
}
|
||||
|
||||
void addName(const QString & name)
|
||||
{
|
||||
names.push_back(name);
|
||||
}
|
||||
|
||||
QString title;
|
||||
QStringList names;
|
||||
};
|
||||
|
||||
public:
|
||||
explicit ContributorsDialog(QWidget * parent = 0);
|
||||
~ContributorsDialog();
|
||||
explicit CreditsDialog(QWidget * parent = 0);
|
||||
~CreditsDialog();
|
||||
|
||||
private:
|
||||
Ui::HtmlDialog * ui;
|
||||
QList<CreditsSection> readCredits();
|
||||
QString sectionTitle(const QString & title);
|
||||
QString formatTable(const QString & title, const QStringList & names, int colums);
|
||||
};
|
||||
|
||||
#endif // _CONTRIBUTORSDIALOG_H_
|
||||
#endif // _CREDITSDIALOG_H_
|
||||
@@ -508,9 +508,9 @@ QString RawSource::toString(const ModelData * model, const GeneralSettings * con
|
||||
int genAryIdx = 0;
|
||||
switch (type) {
|
||||
case SOURCE_TYPE_VIRTUAL_INPUT:
|
||||
result = QObject::tr("[I%1]").arg(index+1);
|
||||
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());
|
||||
result.append(/*":" + */QString(model->inputNames[index]).trimmed());
|
||||
return result;
|
||||
|
||||
case SOURCE_TYPE_LUA_OUTPUT:
|
||||
@@ -544,13 +544,13 @@ QString RawSource::toString(const ModelData * model, const GeneralSettings * con
|
||||
return result;
|
||||
|
||||
case SOURCE_TYPE_CUSTOM_SWITCH:
|
||||
return QObject::tr("LSw%1").arg(index+1, 2, 10, QChar('0'));
|
||||
return RawSwitch(SWITCH_TYPE_VIRTUAL, index+1).toString();
|
||||
|
||||
case SOURCE_TYPE_CYC:
|
||||
return QObject::tr("CYC%1").arg(index+1);
|
||||
|
||||
case SOURCE_TYPE_PPM:
|
||||
return QObject::tr("TR%1").arg(index+1);
|
||||
return QObject::tr("TR%1").arg(index+1, 2, 10, QChar('0'));
|
||||
|
||||
case SOURCE_TYPE_CH:
|
||||
result = QObject::tr("CH%1").arg(index+1, 2, 10, QChar('0'));
|
||||
@@ -564,7 +564,7 @@ QString RawSource::toString(const ModelData * model, const GeneralSettings * con
|
||||
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);
|
||||
result = model ? QString(model->sensorData[qr.quot].label) : QString("[T%1]").arg(qr.quot+1, 2, 10, QChar('0'));
|
||||
if (qr.rem)
|
||||
result += (qr.rem == 1 ? "-" : "+");
|
||||
return result;
|
||||
@@ -574,7 +574,7 @@ QString RawSource::toString(const ModelData * model, const GeneralSettings * con
|
||||
}
|
||||
|
||||
case SOURCE_TYPE_GVAR:
|
||||
result = QObject::tr("GV%1").arg(index+1);
|
||||
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;
|
||||
@@ -682,7 +682,7 @@ QString RawSwitch::toString(Board::Type board, const GeneralSettings * const gen
|
||||
}
|
||||
|
||||
case SWITCH_TYPE_VIRTUAL:
|
||||
return QObject::tr("LSw%1").arg(index, 2, 10, QChar('0'));
|
||||
return QObject::tr("L%1").arg(index, 2, 10, QChar('0'));
|
||||
|
||||
case SWITCH_TYPE_MULTIPOS_POT:
|
||||
if (!getCurrentFirmware()->getCapability(MultiposPotsPositions))
|
||||
|
||||
@@ -884,7 +884,7 @@ class FlightModeField: public TransformedField {
|
||||
virtual void beforeExport()
|
||||
{
|
||||
for (int i=0; i<CPN_MAX_STICKS+MAX_AUX_TRIMS(board); i++) {
|
||||
if (IS_HORUS_OR_TARANIS(board) && version >= 216) {
|
||||
if ((IS_HORUS_OR_TARANIS(board) && version >= 216) || (IS_ARM(board) && version >= 218)) {
|
||||
if (phase.trimMode[i] < 0)
|
||||
trimMode[i] = TRIM_MODE_NONE;
|
||||
else
|
||||
@@ -912,7 +912,7 @@ class FlightModeField: public TransformedField {
|
||||
virtual void afterImport()
|
||||
{
|
||||
for (int i=0; i<CPN_MAX_STICKS+MAX_AUX_TRIMS(board); i++) {
|
||||
if (IS_HORUS_OR_TARANIS(board) && version >= 216) {
|
||||
if ((IS_HORUS_OR_TARANIS(board) && version >= 216) || (IS_ARM(board) && version >= 218)) {
|
||||
if (trimMode[i] == TRIM_MODE_NONE) {
|
||||
phase.trimMode[i] = -1;
|
||||
}
|
||||
@@ -1207,7 +1207,7 @@ class MixField: public TransformedField {
|
||||
|
||||
if (mix.srcRaw.type != SOURCE_TYPE_NONE) {
|
||||
mix.destCh = _destCh + 1;
|
||||
if (!IS_STM32(board) || version < 216) {
|
||||
if (!IS_ARM(board) || (!IS_STM32(board) && version < 218) || version < 216) {
|
||||
if (!_curveMode)
|
||||
mix.curve = CurveReference(CurveReference::CURVE_REF_DIFF, smallGvarToC9x(_curveParam));
|
||||
else if (_curveParam > 6)
|
||||
@@ -1410,7 +1410,7 @@ class InputField: public TransformedField {
|
||||
expo.offset = smallGvarToC9x(_offset);
|
||||
}
|
||||
|
||||
if (!IS_STM32(board) || version < 216) {
|
||||
if (!IS_ARM(board) || (!IS_STM32(board) && version < 218) || version < 216) {
|
||||
if (!_curveMode)
|
||||
expo.curve = CurveReference(CurveReference::CURVE_REF_EXPO, smallGvarToC9x(_curveParam));
|
||||
else if (_curveParam > 6)
|
||||
|
||||
@@ -102,7 +102,7 @@ void FlashEEpromDialog::updateUI()
|
||||
|
||||
void FlashEEpromDialog::on_eepromLoad_clicked()
|
||||
{
|
||||
QString filename = QFileDialog::getOpenFileName(this, tr("Choose Radio Backup file"), g.eepromDir(), tr(EXTERNAL_EEPROM_FILES_FILTER));
|
||||
QString filename = QFileDialog::getOpenFileName(this, tr("Choose Radio Backup file"), g.eepromDir(), EXTERNAL_EEPROM_FILES_FILTER);
|
||||
if (!filename.isEmpty()) {
|
||||
eepromFilename = filename;
|
||||
updateUI();
|
||||
|
||||
@@ -34,12 +34,6 @@ FirmwarePreferencesDialog::FirmwarePreferencesDialog(QWidget *parent) :
|
||||
ui->setupUi(this);
|
||||
setWindowIcon(CompanionIcon("fwpreferences.png"));
|
||||
initSettings();
|
||||
|
||||
foreach(const char *lang, getCurrentFirmware()->getFirmwareBase()->ttslanguages) {
|
||||
ui->voiceCombo->addItem(lang);
|
||||
if (Firmware::getCurrentVariant()->getId().contains(QString("-tts%1").arg(lang)))
|
||||
ui->voiceCombo->setCurrentIndex(ui->voiceCombo->count() - 1);
|
||||
}
|
||||
}
|
||||
|
||||
FirmwarePreferencesDialog::~FirmwarePreferencesDialog()
|
||||
@@ -70,13 +64,13 @@ void FirmwarePreferencesDialog::on_fw_dnld_clicked()
|
||||
initSettings();
|
||||
}
|
||||
|
||||
void FirmwarePreferencesDialog::on_voice_dnld_clicked()
|
||||
void FirmwarePreferencesDialog::on_sd_dnld_clicked()
|
||||
{
|
||||
QString url = "http://voices-21.open-tx.org/";
|
||||
QString url = "http://downloads.open-tx.org/2.2/sdcard/";
|
||||
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/%2/").arg(firmware).arg(ui->voiceCombo->currentText().toLower()));
|
||||
url.append(QString("%1/").arg(firmware));
|
||||
QDesktopServices::openUrl(url);
|
||||
}
|
||||
|
||||
|
||||
@@ -45,7 +45,7 @@ class FirmwarePreferencesDialog : public QDialog
|
||||
|
||||
private slots:
|
||||
void on_fw_dnld_clicked();
|
||||
void on_voice_dnld_clicked();
|
||||
void on_sd_dnld_clicked();
|
||||
void on_checkFWUpdates_clicked();
|
||||
};
|
||||
|
||||
|
||||
@@ -26,13 +26,22 @@
|
||||
<string>Downloads</string>
|
||||
</property>
|
||||
<layout class="QGridLayout" name="gridLayout">
|
||||
<property name="leftMargin">
|
||||
<number>6</number>
|
||||
</property>
|
||||
<property name="topMargin">
|
||||
<number>6</number>
|
||||
</property>
|
||||
<property name="rightMargin">
|
||||
<number>6</number>
|
||||
</property>
|
||||
<property name="bottomMargin">
|
||||
<number>6</number>
|
||||
</property>
|
||||
<property name="verticalSpacing">
|
||||
<number>2</number>
|
||||
</property>
|
||||
<property name="margin">
|
||||
<number>6</number>
|
||||
</property>
|
||||
<item row="24" column="5">
|
||||
<item row="23" column="3">
|
||||
<widget class="QDialogButtonBox" name="buttonBox">
|
||||
<property name="orientation">
|
||||
<enum>Qt::Horizontal</enum>
|
||||
@@ -42,7 +51,7 @@
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="3" column="5">
|
||||
<item row="3" column="3">
|
||||
<widget class="QPushButton" name="checkFWUpdates">
|
||||
<property name="minimumSize">
|
||||
<size>
|
||||
@@ -55,75 +64,6 @@
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="7" column="0">
|
||||
<widget class="QLabel" name="voiceLabel">
|
||||
<property name="font">
|
||||
<font>
|
||||
<family>Sans Serif</family>
|
||||
<weight>75</weight>
|
||||
<bold>true</bold>
|
||||
</font>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Voice</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="7" column="2">
|
||||
<widget class="QComboBox" name="voiceCombo">
|
||||
<property name="maximumSize">
|
||||
<size>
|
||||
<width>50</width>
|
||||
<height>16777215</height>
|
||||
</size>
|
||||
</property>
|
||||
<property name="toolTip">
|
||||
<string>Set voice language.
|
||||
May be different from firmware language</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="7" column="5">
|
||||
<widget class="QPushButton" name="voice_dnld">
|
||||
<property name="text">
|
||||
<string>Download Voice</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="5" column="5">
|
||||
<widget class="QPushButton" name="fw_dnld">
|
||||
<property name="text">
|
||||
<string>Download FW</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="7" column="3">
|
||||
<spacer name="horizontalSpacer_2">
|
||||
<property name="orientation">
|
||||
<enum>Qt::Horizontal</enum>
|
||||
</property>
|
||||
<property name="sizeHint" stdset="0">
|
||||
<size>
|
||||
<width>40</width>
|
||||
<height>20</height>
|
||||
</size>
|
||||
</property>
|
||||
</spacer>
|
||||
</item>
|
||||
<item row="6" column="0" colspan="6">
|
||||
<widget class="Line" name="voiceLine">
|
||||
<property name="orientation">
|
||||
<enum>Qt::Horizontal</enum>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="23" column="0" colspan="6">
|
||||
<widget class="Line" name="line_6">
|
||||
<property name="orientation">
|
||||
<enum>Qt::Horizontal</enum>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="0" column="0">
|
||||
<widget class="QLabel" name="label_6">
|
||||
<property name="sizePolicy">
|
||||
@@ -147,20 +87,28 @@ May be different from firmware language</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="0" column="2" colspan="4">
|
||||
<widget class="QLabel" name="fwTypeLbl">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Expanding" vsizetype="Preferred">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<item row="5" column="3">
|
||||
<widget class="QPushButton" name="fw_dnld">
|
||||
<property name="text">
|
||||
<string notr="true">FwType</string>
|
||||
<string>Download firmware</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="3" column="2" colspan="2">
|
||||
<item row="22" column="0" colspan="4">
|
||||
<widget class="Line" name="line_6">
|
||||
<property name="orientation">
|
||||
<enum>Qt::Horizontal</enum>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="6" column="3">
|
||||
<widget class="QPushButton" name="sd_dnld">
|
||||
<property name="text">
|
||||
<string>Download SD contents</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="3" column="1" colspan="2">
|
||||
<widget class="QLabel" name="lastRevisionLbl">
|
||||
<property name="text">
|
||||
<string notr="true">-</string>
|
||||
@@ -174,13 +122,38 @@ May be different from firmware language</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="0" column="1" colspan="3">
|
||||
<widget class="QLabel" name="fwTypeLbl">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Expanding" vsizetype="Preferred">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string notr="true">FwType</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="6" column="2">
|
||||
<spacer name="horizontalSpacer_2">
|
||||
<property name="orientation">
|
||||
<enum>Qt::Horizontal</enum>
|
||||
</property>
|
||||
<property name="sizeHint" stdset="0">
|
||||
<size>
|
||||
<width>40</width>
|
||||
<height>20</height>
|
||||
</size>
|
||||
</property>
|
||||
</spacer>
|
||||
</item>
|
||||
</layout>
|
||||
</widget>
|
||||
<tabstops>
|
||||
<tabstop>checkFWUpdates</tabstop>
|
||||
<tabstop>fw_dnld</tabstop>
|
||||
<tabstop>voiceCombo</tabstop>
|
||||
<tabstop>voice_dnld</tabstop>
|
||||
<tabstop>sd_dnld</tabstop>
|
||||
<tabstop>buttonBox</tabstop>
|
||||
</tabstops>
|
||||
<resources>
|
||||
|
||||
@@ -110,6 +110,8 @@ HardwarePanel::HardwarePanel(QWidget * parent, GeneralSettings & generalSettings
|
||||
ui->thrName->hide();
|
||||
ui->ailLabel->hide();
|
||||
ui->ailName->hide();
|
||||
ui->potsTypeSeparator_1->hide();
|
||||
ui->potsTypeSeparator_2->hide();
|
||||
}
|
||||
|
||||
setupPotType(0, ui->pot1Label, ui->pot1Name, ui->pot1Type);
|
||||
@@ -141,10 +143,11 @@ HardwarePanel::HardwarePanel(QWidget * parent, GeneralSettings & generalSettings
|
||||
setupSwitchType(16, ui->sqLabel, ui->sqName, ui->sqType);
|
||||
setupSwitchType(17, ui->srLabel, ui->srName, ui->srType);
|
||||
|
||||
if (IS_HORUS_OR_TARANIS(board) && !IS_TARANIS_X7(board)) {
|
||||
if (IS_TARANIS(board) && !IS_TARANIS_X7(board)) {
|
||||
ui->serialPortMode->setCurrentIndex(generalSettings.hw_uartMode);
|
||||
}
|
||||
else {
|
||||
ui->serialPortMode->setCurrentIndex(0);
|
||||
ui->serialPortMode->hide();
|
||||
ui->serialPortLabel->hide();
|
||||
}
|
||||
@@ -160,8 +163,7 @@ HardwarePanel::HardwarePanel(QWidget * parent, GeneralSettings & generalSettings
|
||||
}
|
||||
else {
|
||||
ui->bluetoothLabel->hide();
|
||||
ui->bluetoothEnable->hide();
|
||||
ui->bluetoothName->hide();
|
||||
ui->bluetoothWidget->hide();
|
||||
}
|
||||
|
||||
if (IS_HORUS_OR_TARANIS(board)) {
|
||||
@@ -188,39 +190,52 @@ void HardwarePanel::on_filterEnable_stateChanged()
|
||||
|
||||
void HardwarePanel::on_PPM_MultiplierDSB_editingFinished()
|
||||
{
|
||||
generalSettings.PPM_Multiplier = (int)(ui->PPM_MultiplierDSB->value()*10)-10;
|
||||
emit modified();
|
||||
int val = (int)(ui->PPM_MultiplierDSB->value()*10)-10;
|
||||
if (generalSettings.PPM_Multiplier != val) {
|
||||
generalSettings.PPM_Multiplier = val;
|
||||
emit modified();
|
||||
}
|
||||
}
|
||||
|
||||
void HardwarePanel::on_PPM1_editingFinished()
|
||||
{
|
||||
generalSettings.trainer.calib[0] = ui->PPM1->value();
|
||||
emit modified();
|
||||
if (generalSettings.trainer.calib[0] != ui->PPM1->value()) {
|
||||
generalSettings.trainer.calib[0] = ui->PPM1->value();
|
||||
emit modified();
|
||||
}
|
||||
}
|
||||
|
||||
void HardwarePanel::on_PPM2_editingFinished()
|
||||
{
|
||||
generalSettings.trainer.calib[1] = ui->PPM2->value();
|
||||
emit modified();
|
||||
if (generalSettings.trainer.calib[1] != ui->PPM2->value()) {
|
||||
generalSettings.trainer.calib[1] = ui->PPM2->value();
|
||||
emit modified();
|
||||
}
|
||||
}
|
||||
|
||||
void HardwarePanel::on_PPM3_editingFinished()
|
||||
{
|
||||
generalSettings.trainer.calib[2] = ui->PPM3->value();
|
||||
emit modified();
|
||||
if (generalSettings.trainer.calib[2] != ui->PPM3->value()) {
|
||||
generalSettings.trainer.calib[2] = ui->PPM3->value();
|
||||
emit modified();
|
||||
}
|
||||
}
|
||||
|
||||
void HardwarePanel::on_PPM4_editingFinished()
|
||||
{
|
||||
generalSettings.trainer.calib[3] = ui->PPM4->value();
|
||||
emit modified();
|
||||
if (generalSettings.trainer.calib[3] != ui->PPM4->value()) {
|
||||
generalSettings.trainer.calib[3] = ui->PPM4->value();
|
||||
emit modified();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void HardwarePanel::on_txCurrentHardware_editingFinished()
|
||||
void HardwarePanel::on_txCurrentCalibration_editingFinished()
|
||||
{
|
||||
generalSettings.txCurrentCalibration = ui->txCurrentCalibration->value();
|
||||
emit modified();
|
||||
if (generalSettings.txCurrentCalibration != ui->txCurrentCalibration->value()) {
|
||||
generalSettings.txCurrentCalibration = ui->txCurrentCalibration->value();
|
||||
emit modified();
|
||||
}
|
||||
}
|
||||
|
||||
void HardwarePanel::on_bluetoothEnable_stateChanged(int)
|
||||
@@ -241,10 +256,12 @@ void HardwarePanel::setValues()
|
||||
ui->PPM_MultiplierDSB->setValue((qreal)(generalSettings.PPM_Multiplier+10)/10);
|
||||
}
|
||||
|
||||
void HardwarePanel::on_txVoltageHardware_editingFinished()
|
||||
void HardwarePanel::on_txVoltageCalibration_editingFinished()
|
||||
{
|
||||
generalSettings.txVoltageCalibration = ui->txVoltageCalibration->value()*10;
|
||||
emit modified();
|
||||
if (generalSettings.txVoltageCalibration != ui->txVoltageCalibration->value()*10) {
|
||||
generalSettings.txVoltageCalibration = ui->txVoltageCalibration->value()*10;
|
||||
emit modified();
|
||||
}
|
||||
}
|
||||
|
||||
void HardwarePanel::on_serialPortMode_currentIndexChanged(int index)
|
||||
|
||||
@@ -40,14 +40,14 @@ class HardwarePanel : public GeneralPanel
|
||||
virtual ~HardwarePanel();
|
||||
|
||||
private slots:
|
||||
void on_txVoltageHardware_editingFinished();
|
||||
void on_PPM1_editingFinished();
|
||||
void on_PPM2_editingFinished();
|
||||
void on_PPM3_editingFinished();
|
||||
void on_PPM4_editingFinished();
|
||||
void on_PPM_MultiplierDSB_editingFinished();
|
||||
|
||||
void on_txCurrentHardware_editingFinished();
|
||||
void on_txCurrentCalibration_editingFinished();
|
||||
void on_txVoltageCalibration_editingFinished();
|
||||
void on_bluetoothEnable_stateChanged(int);
|
||||
void on_filterEnable_stateChanged();
|
||||
|
||||
|
||||
@@ -6,14 +6,23 @@
|
||||
<rect>
|
||||
<x>0</x>
|
||||
<y>0</y>
|
||||
<width>359</width>
|
||||
<height>1594</height>
|
||||
<width>470</width>
|
||||
<height>1095</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Preferred" vsizetype="Maximum">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="windowTitle">
|
||||
<string>Form</string>
|
||||
</property>
|
||||
<layout class="QGridLayout" name="gridLayout_2" rowstretch="0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0" columnstretch="0,0,0,0,0">
|
||||
<layout class="QGridLayout" name="gridLayout_2">
|
||||
<property name="spacing">
|
||||
<number>6</number>
|
||||
</property>
|
||||
<item row="29" column="0">
|
||||
<widget class="QLabel" name="sqLabel">
|
||||
<property name="text">
|
||||
@@ -125,19 +134,6 @@
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="12" column="0" colspan="5">
|
||||
<widget class="Line" name="potsTypeSeparator_2">
|
||||
<property name="minimumSize">
|
||||
<size>
|
||||
<width>0</width>
|
||||
<height>10</height>
|
||||
</size>
|
||||
</property>
|
||||
<property name="orientation">
|
||||
<enum>Qt::Horizontal</enum>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="5" column="1">
|
||||
<widget class="AutoLineEdit" name="pot2Name">
|
||||
<property name="maxLength">
|
||||
@@ -730,32 +726,6 @@
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="31" column="0" colspan="4">
|
||||
<widget class="Line" name="potsTypeSeparator_3">
|
||||
<property name="minimumSize">
|
||||
<size>
|
||||
<width>0</width>
|
||||
<height>10</height>
|
||||
</size>
|
||||
</property>
|
||||
<property name="orientation">
|
||||
<enum>Qt::Horizontal</enum>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="38" column="0" colspan="4">
|
||||
<widget class="Line" name="potsTypeSeparator_4">
|
||||
<property name="minimumSize">
|
||||
<size>
|
||||
<width>0</width>
|
||||
<height>10</height>
|
||||
</size>
|
||||
</property>
|
||||
<property name="orientation">
|
||||
<enum>Qt::Horizontal</enum>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="25" column="0">
|
||||
<widget class="QLabel" name="smLabel">
|
||||
<property name="text">
|
||||
@@ -1075,6 +1045,12 @@
|
||||
</item>
|
||||
<item row="32" column="0">
|
||||
<widget class="QLabel" name="bluetoothLabel">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Preferred" vsizetype="Fixed">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string>Bluetooth</string>
|
||||
</property>
|
||||
@@ -1090,24 +1066,6 @@
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="32" column="1">
|
||||
<layout class="QHBoxLayout" name="horizontalLayout">
|
||||
<item>
|
||||
<widget class="QCheckBox" name="bluetoothEnable">
|
||||
<property name="text">
|
||||
<string/>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="AutoLineEdit" name="bluetoothName">
|
||||
<property name="maxLength">
|
||||
<number>10</number>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
</layout>
|
||||
</item>
|
||||
<item row="33" column="1">
|
||||
<widget class="QCheckBox" name="filterEnable">
|
||||
<property name="text">
|
||||
@@ -1122,19 +1080,116 @@
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="32" column="1">
|
||||
<widget class="QWidget" name="bluetoothWidget" native="true">
|
||||
<layout class="QHBoxLayout" name="horizontalLayout">
|
||||
<property name="spacing">
|
||||
<number>6</number>
|
||||
</property>
|
||||
<property name="leftMargin">
|
||||
<number>0</number>
|
||||
</property>
|
||||
<property name="topMargin">
|
||||
<number>0</number>
|
||||
</property>
|
||||
<property name="rightMargin">
|
||||
<number>0</number>
|
||||
</property>
|
||||
<property name="bottomMargin">
|
||||
<number>0</number>
|
||||
</property>
|
||||
<item>
|
||||
<widget class="QCheckBox" name="bluetoothEnable">
|
||||
<property name="text">
|
||||
<string/>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<spacer name="horizontalSpacer">
|
||||
<property name="orientation">
|
||||
<enum>Qt::Horizontal</enum>
|
||||
</property>
|
||||
<property name="sizeType">
|
||||
<enum>QSizePolicy::Fixed</enum>
|
||||
</property>
|
||||
<property name="sizeHint" stdset="0">
|
||||
<size>
|
||||
<width>5</width>
|
||||
<height>20</height>
|
||||
</size>
|
||||
</property>
|
||||
</spacer>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QLabel" name="btNameLabel">
|
||||
<property name="text">
|
||||
<string>Device Name:</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="AutoLineEdit" name="bluetoothName">
|
||||
<property name="maxLength">
|
||||
<number>10</number>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
</layout>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="31" column="0" colspan="3">
|
||||
<widget class="Line" name="potsTypeSeparator_2">
|
||||
<property name="minimumSize">
|
||||
<size>
|
||||
<width>0</width>
|
||||
<height>10</height>
|
||||
</size>
|
||||
</property>
|
||||
<property name="orientation">
|
||||
<enum>Qt::Horizontal</enum>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="38" column="0" colspan="3">
|
||||
<widget class="Line" name="ppmSeparator">
|
||||
<property name="minimumSize">
|
||||
<size>
|
||||
<width>0</width>
|
||||
<height>10</height>
|
||||
</size>
|
||||
</property>
|
||||
<property name="orientation">
|
||||
<enum>Qt::Horizontal</enum>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item row="12" column="0" colspan="3">
|
||||
<widget class="Line" name="potsTypeSeparator_1">
|
||||
<property name="minimumSize">
|
||||
<size>
|
||||
<width>0</width>
|
||||
<height>10</height>
|
||||
</size>
|
||||
</property>
|
||||
<property name="orientation">
|
||||
<enum>Qt::Horizontal</enum>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
</layout>
|
||||
</widget>
|
||||
<customwidgets>
|
||||
<customwidget>
|
||||
<class>AutoLineEdit</class>
|
||||
<extends>QLineEdit</extends>
|
||||
<header>autolineedit.h</header>
|
||||
</customwidget>
|
||||
<customwidget>
|
||||
<class>AutoComboBox</class>
|
||||
<extends>QComboBox</extends>
|
||||
<header>autocombobox.h</header>
|
||||
</customwidget>
|
||||
<customwidget>
|
||||
<class>AutoLineEdit</class>
|
||||
<extends>QLineEdit</extends>
|
||||
<header>autolineedit.h</header>
|
||||
</customwidget>
|
||||
</customwidgets>
|
||||
<resources/>
|
||||
<connections/>
|
||||
|
||||
+313
-52
@@ -30,7 +30,7 @@
|
||||
#include "downloaddialog.h"
|
||||
#include "printdialog.h"
|
||||
#include "version.h"
|
||||
#include "contributorsdialog.h"
|
||||
#include "creditsdialog.h"
|
||||
#include "releasenotesdialog.h"
|
||||
#include "releasenotesfirmwaredialog.h"
|
||||
#include "customizesplashdialog.h"
|
||||
@@ -44,6 +44,7 @@
|
||||
#include "process_sync.h"
|
||||
#include "radiointerface.h"
|
||||
#include "progressdialog.h"
|
||||
#include "progresswidget.h"
|
||||
#include "storage.h"
|
||||
#include "translations.h"
|
||||
|
||||
@@ -52,22 +53,28 @@
|
||||
#include <QFileInfo>
|
||||
#include <QDesktopServices>
|
||||
|
||||
#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__
|
||||
#define COMPANION_STAMP "companion-macosx.stamp"
|
||||
#define COMPANION_INSTALLER "companion-macosx-%1.dmg"
|
||||
#else
|
||||
#define COMPANION_INSTALLER "macosx/opentx-companion-%1.dmg"
|
||||
#define COMPANION_FILEMASK tr("Diskimage (*.dmg)")
|
||||
#define COMPANION_INSTALL_QUESTION tr("Would you like to open the disk image to install the new version?")
|
||||
#elif WIN32
|
||||
#define COMPANION_STAMP "companion-windows.stamp"
|
||||
#define COMPANION_INSTALLER "companion-windows-%1.exe"
|
||||
#define COMPANION_INSTALLER "windows/companion-windows-%1.exe"
|
||||
#define COMPANION_FILEMASK tr("Executable (*.exe)")
|
||||
#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_FILEMASK "*.*"
|
||||
#define COMPANION_INSTALL_QUESTION tr("Would you like to launch the installer?")
|
||||
#endif
|
||||
|
||||
#ifdef WIN32
|
||||
#define OPENTX_NIGHT_COMPANION_DOWNLOADS "http://downloads-22.open-tx.org/nightly/companion/windows"
|
||||
#else
|
||||
#define OPENTX_NIGHT_COMPANION_DOWNLOADS "http://downloads-22.open-tx.org/nightly/companion/linux"
|
||||
#endif
|
||||
#define OPENTX_NIGHT_COMPANION_DOWNLOADS "http://downloads-22.open-tx.org/nightlies/companion"
|
||||
|
||||
MainWindow::MainWindow():
|
||||
downloadDialog_forWait(NULL),
|
||||
@@ -108,7 +115,16 @@ MainWindow::MainWindow():
|
||||
if (showSplash) {
|
||||
updateDelay += (SPLASH_TIME*1000);
|
||||
}
|
||||
QTimer::singleShot(updateDelay, this, SLOT(doAutoUpdates()));
|
||||
|
||||
if (g.isFirstUse()) {
|
||||
g.warningId(g.warningId() | AppMessages::MSG_WELCOME);
|
||||
QTimer::singleShot(updateDelay-500, this, SLOT(appPrefs())); // must be shown before warnings dialog but after splash
|
||||
}
|
||||
else {
|
||||
if (!g.previousVersion().isEmpty())
|
||||
g.warningId(g.warningId() | AppMessages::MSG_UPGRADED);
|
||||
QTimer::singleShot(updateDelay, this, SLOT(doAutoUpdates()));
|
||||
}
|
||||
QTimer::singleShot(updateDelay, this, SLOT(displayWarnings()));
|
||||
|
||||
QStringList strl = QApplication::arguments();
|
||||
@@ -161,21 +177,39 @@ MainWindow::~MainWindow()
|
||||
|
||||
void MainWindow::displayWarnings()
|
||||
{
|
||||
int warnId = g.warningId();
|
||||
if (warnId<WARNING_ID && warnId!=0) {
|
||||
int res=0;
|
||||
if (WARNING_LEVEL>0)
|
||||
QMessageBox::warning(this, "Companion", WARNING);
|
||||
else
|
||||
QMessageBox::about(this, "Companion", WARNING);
|
||||
res = QMessageBox::question(this, "Companion", tr("Display previous warning again at startup ?"), QMessageBox::Yes | QMessageBox::No);
|
||||
if (res == QMessageBox::No) {
|
||||
g.warningId(WARNING_ID);
|
||||
}
|
||||
using namespace AppMessages;
|
||||
static uint shownMsgs = 0;
|
||||
int showMsgs = g.warningId();
|
||||
int msgId;
|
||||
QString infoTxt;
|
||||
|
||||
if ((showMsgs & MSG_WELCOME) && !(shownMsgs & MSG_WELCOME)) {
|
||||
infoTxt = CPN_STR_MSG_WELCOME.arg(VERSION);
|
||||
msgId = MSG_WELCOME;
|
||||
}
|
||||
else if (warnId==0) {
|
||||
g.warningId(WARNING_ID);
|
||||
else if ((showMsgs & MSG_UPGRADED) && !(shownMsgs & MSG_UPGRADED)) {
|
||||
infoTxt = CPN_STR_MSG_UPGRADED.arg(VERSION);
|
||||
msgId = MSG_UPGRADED;
|
||||
}
|
||||
else {
|
||||
return;
|
||||
}
|
||||
|
||||
QMessageBox msgBox(this);
|
||||
msgBox.setWindowTitle(tr("Companion"));
|
||||
msgBox.setIcon(QMessageBox::Information);
|
||||
msgBox.setStandardButtons(QMessageBox::Ok);
|
||||
msgBox.setInformativeText(infoTxt);
|
||||
QCheckBox * cb = new QCheckBox(tr("Show this message again at next startup?"), &msgBox);
|
||||
msgBox.setCheckBox(cb);
|
||||
|
||||
msgBox.exec();
|
||||
|
||||
shownMsgs |= msgId;
|
||||
if (!cb->isChecked())
|
||||
g.warningId(showMsgs & ~msgId);
|
||||
|
||||
displayWarnings(); // in case more warnings need showing
|
||||
}
|
||||
|
||||
void MainWindow::doAutoUpdates()
|
||||
@@ -288,20 +322,20 @@ void MainWindow::checkForCompanionUpdateFinished(QNetworkReply * reply)
|
||||
if (version.isNull())
|
||||
return onUpdatesError();
|
||||
|
||||
int vnum = version2index(version);
|
||||
int webVersion = version2index(version);
|
||||
|
||||
QString c9xversion = QString(VERSION);
|
||||
int c9xver = version2index(c9xversion);
|
||||
int ownVersion = version2index(VERSION);
|
||||
|
||||
if (c9xver < vnum) {
|
||||
#if defined WIN32 || !defined __GNUC__ // || defined __APPLE__ // OSX should only notify of updates since no update packages are available.
|
||||
if (ownVersion < webVersion) {
|
||||
#if defined WIN32 || defined __APPLE__
|
||||
int ret = QMessageBox::question(this, "Companion", tr("A new version of Companion is available (version %1)<br>"
|
||||
"Would you like to download it?").arg(version) ,
|
||||
QMessageBox::Yes | QMessageBox::No);
|
||||
|
||||
if (ret == QMessageBox::Yes) {
|
||||
QDir dir(g.updatesDir());
|
||||
QString fileName = QFileDialog::getSaveFileName(this, tr("Save As"), dir.absoluteFilePath(QString(COMPANION_INSTALLER).arg(version)), tr("Executable (*.exe)"));
|
||||
QString fileName = QFileDialog::getSaveFileName(this, tr("Save As"), dir.absoluteFilePath(QString(COMPANION_INSTALLER).arg(version)), COMPANION_FILEMASK);
|
||||
|
||||
if (!fileName.isEmpty()) {
|
||||
g.updatesDir(QFileInfo(fileName).dir().absolutePath());
|
||||
downloadDialog * dd = new downloadDialog(this, QString("%1/%2").arg(getCompanionUpdateBaseUrl()).arg(QString(COMPANION_INSTALLER).arg(version)), fileName);
|
||||
@@ -311,7 +345,7 @@ void MainWindow::checkForCompanionUpdateFinished(QNetworkReply * reply)
|
||||
}
|
||||
}
|
||||
#else
|
||||
QMessageBox::warning(this, tr("New release available"), tr("A new release of Companion is available, please check the OpenTX website!"));
|
||||
QMessageBox::warning(this, tr("New release available"), tr("A new release of Companion is available, please check the <a href='%1'>OpenTX website!</a>").arg(OPENTX_DOWNLOADS_PAGE_URL));
|
||||
#endif
|
||||
}
|
||||
else {
|
||||
@@ -325,8 +359,7 @@ void MainWindow::checkForCompanionUpdateFinished(QNetworkReply * reply)
|
||||
|
||||
void MainWindow::updateDownloaded()
|
||||
{
|
||||
int ret = QMessageBox::question(this, "Companion", tr("Would you like to launch the installer?") ,
|
||||
QMessageBox::Yes | QMessageBox::No);
|
||||
int ret = QMessageBox::question(this, "Companion", COMPANION_INSTALL_QUESTION, QMessageBox::Yes | QMessageBox::No);
|
||||
if (ret == QMessageBox::Yes) {
|
||||
if (QDesktopServices::openUrl(QUrl::fromLocalFile(installer_fileName)))
|
||||
QApplication::exit();
|
||||
@@ -657,9 +690,7 @@ void MainWindow::openFile(const QString & fileName, bool updateLastUsedDir)
|
||||
|
||||
void MainWindow::openFile()
|
||||
{
|
||||
QString fileFilter;
|
||||
fileFilter = tr(EEPROM_FILES_FILTER);
|
||||
QString fileName = QFileDialog::getOpenFileName(this, tr("Open Models and Settings file"), g.eepromDir(), fileFilter);
|
||||
QString fileName = QFileDialog::getOpenFileName(this, tr("Open Models and Settings file"), g.eepromDir(), EEPROM_FILES_FILTER);
|
||||
openFile(fileName);
|
||||
}
|
||||
|
||||
@@ -732,29 +763,259 @@ void MainWindow::fwPrefs()
|
||||
|
||||
void MainWindow::contributors()
|
||||
{
|
||||
ContributorsDialog * dialog = new ContributorsDialog(this);
|
||||
CreditsDialog * dialog = new CreditsDialog(this);
|
||||
dialog->exec();
|
||||
dialog->deleteLater();
|
||||
}
|
||||
|
||||
// Create a widget with a line edit and folder select button and handles all interactions. Features autosuggest
|
||||
// path hints while typing, invalid paths shown in red. The label string is only for dialog title, not a QLabel.
|
||||
// This should probably be moved some place more reusable, esp. the QFileSystemModel.
|
||||
QWidget * folderSelectorWidget(QString * path, const QString & label, QWidget * parent)
|
||||
{
|
||||
static QFileSystemModel fileModel;
|
||||
static bool init = false;
|
||||
if (!init) {
|
||||
init = true;
|
||||
fileModel.setFilter(QDir::Dirs);
|
||||
fileModel.setRootPath("/");
|
||||
}
|
||||
|
||||
QWidget * fsw = new QWidget(parent);
|
||||
QLineEdit * le = new QLineEdit(parent);
|
||||
QCompleter * fsc = new QCompleter(fsw);
|
||||
fsc->setModel(&fileModel);
|
||||
//fsc->setCompletionMode(QCompleter::InlineCompletion);
|
||||
le->setCompleter(fsc);
|
||||
|
||||
QToolButton * btn = new QToolButton(fsw);
|
||||
btn->setIcon(CompanionIcon("open.png"));
|
||||
QHBoxLayout * l = new QHBoxLayout(fsw);
|
||||
l->setContentsMargins(0,0,0,0);
|
||||
l->setSpacing(3);
|
||||
l->addWidget(le);
|
||||
l->addWidget(btn);
|
||||
|
||||
QObject::connect(btn, &QToolButton::clicked, [=]() {
|
||||
QString dir = QFileDialog::getExistingDirectory(parent, label, le->text(), 0);
|
||||
if (!dir.isEmpty()) {
|
||||
le->setText(QDir::toNativeSeparators(dir));
|
||||
le->setFocus();
|
||||
}
|
||||
});
|
||||
|
||||
QObject::connect(le, &QLineEdit::textChanged, [=](const QString & text) {
|
||||
*path = text;
|
||||
if (QFile::exists(text))
|
||||
le->setStyleSheet("");
|
||||
else
|
||||
le->setStyleSheet("QLineEdit {color: red;}");
|
||||
});
|
||||
le->setText(QDir::toNativeSeparators(*path));
|
||||
|
||||
return fsw;
|
||||
}
|
||||
|
||||
void MainWindow::sdsync()
|
||||
{
|
||||
QString sdPath = g.profile[g.id()].sdPath();
|
||||
if (sdPath.isEmpty()) {
|
||||
QMessageBox::warning(this, QObject::tr("Synchronization error"), QObject::tr("No SD directory configured!"));
|
||||
const QString dlgTtl = tr("Synchronize SD");
|
||||
const QIcon dlgIcn = CompanionIcon("sdsync.png");
|
||||
const QString srcArw = CPN_STR_SW_INDICATOR_UP % " ";
|
||||
const QString dstArw = CPN_STR_SW_INDICATOR_DN % " ";
|
||||
QStringList errorMsgs;
|
||||
|
||||
// remember user-selectable options for duration of session
|
||||
static QString sourcePath;
|
||||
static QString destPath;
|
||||
static int syncDirection = SyncProcess::SYNC_A2B_B2A;
|
||||
static int compareType = SyncProcess::OVERWR_NEWER_IF_DIFF;
|
||||
static int maxFileSize = 2 * 1024 * 1024; // Bytes
|
||||
static bool dryRun = false;
|
||||
|
||||
if (sourcePath.isEmpty())
|
||||
sourcePath = g.profile[g.id()].sdPath();
|
||||
if (destPath.isEmpty())
|
||||
destPath = findMassstoragePath("SOUNDS").replace(QRegExp("[/\\\\]?SOUNDS"), "");
|
||||
|
||||
if (sourcePath.isEmpty())
|
||||
errorMsgs << tr("No local SD structure path configured!");
|
||||
if (destPath.isEmpty())
|
||||
errorMsgs << tr("No Radio or SD card detected!");
|
||||
|
||||
QDialog dlg(this);
|
||||
dlg.setWindowTitle(dlgTtl % tr(" :: Options"));
|
||||
dlg.setWindowIcon(dlgIcn);
|
||||
dlg.setSizeGripEnabled(true);
|
||||
dlg.setWindowFlags(dlg.windowFlags() & ~Qt::WindowContextHelpButtonHint);
|
||||
|
||||
QLabel * lblSrc = new QLabel(tr("Local Folder:"), &dlg);
|
||||
QWidget * wdgSrc = folderSelectorWidget(&sourcePath, lblSrc->text(), &dlg);
|
||||
|
||||
QLabel * lblDst = new QLabel(tr("Radio Folder:"), &dlg);
|
||||
QWidget * wdgDst = folderSelectorWidget(&destPath, lblDst->text(), &dlg);
|
||||
|
||||
QLabel * lbDir = new QLabel(tr("Sync. Direction:"), &dlg);
|
||||
QComboBox * syncDir = new QComboBox(&dlg);
|
||||
syncDir->addItem(tr("%1%2 Both directions, to radio folder first").arg(dstArw, srcArw), SyncProcess::SYNC_A2B_B2A);
|
||||
syncDir->addItem(tr("%1%2 Both directions, to local folder first").arg(srcArw, dstArw), SyncProcess::SYNC_B2A_A2B);
|
||||
syncDir->addItem(tr(" %1 Only from local folder to radio folder").arg(dstArw), SyncProcess::SYNC_A2B);
|
||||
syncDir->addItem(tr(" %1 Only from radio folder to local folder").arg(srcArw), SyncProcess::SYNC_B2A);
|
||||
syncDir->setCurrentIndex(-1); // we set the default option later
|
||||
|
||||
QLabel * lbMode = new QLabel(tr("Existing Files:"), &dlg);
|
||||
QComboBox * copyMode = new QComboBox(&dlg);
|
||||
copyMode->setToolTip(tr("How to handle overwriting files which already exist in the destination folder."));
|
||||
copyMode->addItem(tr("Copy only if newer and different (compare contents)"), SyncProcess::OVERWR_NEWER_IF_DIFF);
|
||||
copyMode->addItem(tr("Copy only if newer (do not compare contents)"), SyncProcess::OVERWR_NEWER_ALWAYS);
|
||||
copyMode->addItem(tr("Copy only if different (ignore file time stamps)"), SyncProcess::OVERWR_IF_DIFF);
|
||||
copyMode->addItem(tr("Always copy (force overwite existing files)"), SyncProcess::OVERWR_ALWAYS);
|
||||
|
||||
QLabel * lbSize = new QLabel(tr("Max. File Size:"), &dlg);
|
||||
QSpinBox * maxSize = new QSpinBox(&dlg);
|
||||
maxSize->setRange(0, 100 * 1024);
|
||||
maxSize->setAccelerated(true);
|
||||
maxSize->setSpecialValueText(tr("Any size"));
|
||||
maxSize->setToolTip(tr("Skip files larger than this size. Enter zero for unlimited."));
|
||||
#if (QT_VERSION >= QT_VERSION_CHECK(5, 3, 0))
|
||||
maxSize->setGroupSeparatorShown(true);
|
||||
#endif
|
||||
|
||||
QCheckBox * testRun = new QCheckBox(tr("Test-run only"), &dlg);
|
||||
testRun->setToolTip(tr("Run as normal but do not actually copy anything. Useful for verifying results before real sync."));
|
||||
connect(testRun, &QCheckBox::toggled, [=](bool on) { dryRun = on; });
|
||||
|
||||
// layout to hold size spinbox and checkbox option(s)
|
||||
QHBoxLayout * hlay1 = new QHBoxLayout();
|
||||
hlay1->addWidget(maxSize, 1);
|
||||
hlay1->addWidget(testRun);
|
||||
|
||||
// dialog OK/Cancel buttons
|
||||
QDialogButtonBox * bb = new QDialogButtonBox(QDialogButtonBox::Ok | QDialogButtonBox::Cancel, &dlg);
|
||||
|
||||
// Create main layout and add everything
|
||||
QGridLayout * dlgL = new QGridLayout(&dlg);
|
||||
dlgL->setSizeConstraint(QLayout::SetFixedSize);
|
||||
int row = 0;
|
||||
if (errorMsgs.size()) {
|
||||
QLabel * lblWarn = new QLabel(QString(errorMsgs.join('\n')), &dlg);
|
||||
lblWarn->setStyleSheet("QLabel { color: red; }");
|
||||
dlgL->addWidget(lblWarn, row++, 0, 1, 2);
|
||||
}
|
||||
dlgL->addWidget(lblSrc, row, 0);
|
||||
dlgL->addWidget(wdgSrc, row++, 1);
|
||||
dlgL->addWidget(lblDst, row, 0);
|
||||
dlgL->addWidget(wdgDst, row++, 1);
|
||||
dlgL->addWidget(lbDir, row, 0);
|
||||
dlgL->addWidget(syncDir, row++, 1);
|
||||
dlgL->addWidget(lbMode, row, 0);
|
||||
dlgL->addWidget(copyMode, row++, 1);
|
||||
dlgL->addWidget(lbSize, row, 0);
|
||||
dlgL->addLayout(hlay1, row++, 1);
|
||||
dlgL->addWidget(bb, row++, 0, 1, 2);
|
||||
dlgL->setRowStretch(row, 1);
|
||||
|
||||
connect(copyMode, static_cast<void(QComboBox::*)(int)>(&QComboBox::currentIndexChanged), [=](int) {
|
||||
compareType = copyMode->currentData().toInt();
|
||||
});
|
||||
|
||||
// function to dis/enable the OVERWR_ALWAYS option depending on sync direction
|
||||
connect(syncDir, static_cast<void(QComboBox::*)(int)>(&QComboBox::currentIndexChanged), [=](int) {
|
||||
int dir = syncDir->currentData().toInt();
|
||||
int idx = copyMode->findData(SyncProcess::OVERWR_ALWAYS);
|
||||
int flg = (dir == SyncProcess::SYNC_A2B || dir == SyncProcess::SYNC_B2A) ? 33 : 0;
|
||||
if (!flg && idx == copyMode->currentIndex())
|
||||
copyMode->setCurrentIndex(copyMode->findData(SyncProcess::OVERWR_NEWER_IF_DIFF));
|
||||
copyMode->setItemData(idx, flg, Qt::UserRole - 1);
|
||||
syncDirection = dir;
|
||||
});
|
||||
|
||||
// function to set magnitude of file size spinbox, KB or MB
|
||||
connect(maxSize, static_cast<void(QSpinBox::*)(int)>(&QSpinBox::valueChanged), [=](int value) {
|
||||
int multi = maxSize->property("multi").isValid() ? maxSize->property("multi").toInt() : 0;
|
||||
maxSize->blockSignals(true);
|
||||
if (value >= 10 * 1024 && multi != 1024 * 1024) {
|
||||
// KB -> MB
|
||||
multi = 1024 * 1024;
|
||||
maxSize->setValue(value / 1024);
|
||||
maxSize->setMaximum(100);
|
||||
maxSize->setSingleStep(1);
|
||||
maxSize->setSuffix(tr(" MB"));
|
||||
}
|
||||
else if ((value < 10 && multi != 1024) || !multi) {
|
||||
// MB -> KB
|
||||
if (multi)
|
||||
value *= 1024;
|
||||
multi = 1024;
|
||||
if (value == 9 * 1024)
|
||||
value += 1024 - 32; // avoid large jump when stepping from 10MB to 10,208KB
|
||||
maxSize->setMaximum(100 * 1024);
|
||||
maxSize->setValue(value);
|
||||
maxSize->setSingleStep(32);
|
||||
maxSize->setSuffix(tr(" KB"));
|
||||
}
|
||||
maxSize->setProperty("multi", multi);
|
||||
maxSize->blockSignals(false);
|
||||
maxFileSize = value * multi;
|
||||
});
|
||||
|
||||
copyMode->setCurrentIndex(copyMode->findData(compareType));
|
||||
syncDir->setCurrentIndex(syncDir->findData(syncDirection));
|
||||
maxSize->setValue(maxFileSize / 1024);
|
||||
testRun->setChecked(dryRun);
|
||||
|
||||
connect(bb, &QDialogButtonBox::accepted, &dlg, &QDialog::accept);
|
||||
connect(bb, &QDialogButtonBox::rejected, &dlg, &QDialog::reject);
|
||||
|
||||
// to restart dialog on error/etc
|
||||
openDialog:
|
||||
|
||||
// show the modal options dialog
|
||||
if (dlg.exec() == QDialog::Rejected)
|
||||
return;
|
||||
|
||||
// validate
|
||||
errorMsgs.clear();
|
||||
if (sourcePath == destPath)
|
||||
errorMsgs << tr("Source and destination folders are the same!");
|
||||
if (sourcePath.isEmpty() || !QFile::exists(sourcePath))
|
||||
errorMsgs << tr("Source folder not found: %1").arg(sourcePath);
|
||||
if (destPath.isEmpty() || !QFile::exists(destPath))
|
||||
errorMsgs << tr("Destination folder not found: %1").arg(destPath);
|
||||
|
||||
if (!errorMsgs.isEmpty()) {
|
||||
QMessageBox::warning(this, dlgTtl % tr(" :: Error"), errorMsgs.join('\n'));
|
||||
goto openDialog;
|
||||
}
|
||||
QString massstoragePath = findMassstoragePath("SOUNDS");
|
||||
if (massstoragePath.isEmpty()) {
|
||||
QMessageBox::warning(this, QObject::tr("Synchronization error"), QObject::tr("No Radio connected!"));
|
||||
return;
|
||||
}
|
||||
massstoragePath = massstoragePath.left(massstoragePath.length() - 7);
|
||||
ProgressDialog progressDialog(this, tr("Synchronize SD"), CompanionIcon("sdsync.png"));
|
||||
SyncProcess syncProcess(massstoragePath, g.profile[g.id()].sdPath(), progressDialog.progress());
|
||||
if (!syncProcess.run()) {
|
||||
progressDialog.exec();
|
||||
}
|
||||
|
||||
// set up the progress dialog and the sync process worker
|
||||
ProgressDialog * progressDlg = new ProgressDialog(this, dlgTtl % tr(" :: Progress"), dlgIcn);
|
||||
progressDlg->setAttribute(Qt::WA_DeleteOnClose, true);
|
||||
ProgressWidget * progWidget = progressDlg->progress();
|
||||
SyncProcess * syncProcess = new SyncProcess(sourcePath, destPath, syncDirection, compareType, maxFileSize, dryRun);
|
||||
|
||||
// move sync process to separate thread, we only use signals/slots from here on...
|
||||
QThread * syncThread = new QThread(this);
|
||||
syncProcess->moveToThread(syncThread);
|
||||
|
||||
// ...and quite a few of them!
|
||||
connect(this, &MainWindow::startSync, syncProcess, &SyncProcess::run);
|
||||
connect(syncThread, &QThread::finished, syncProcess, &SyncProcess::deleteLater);
|
||||
connect(syncProcess, &SyncProcess::finished, syncThread, &QThread::quit);
|
||||
connect(syncProcess, &SyncProcess::destroyed, syncThread, &QThread::quit);
|
||||
connect(syncProcess, &SyncProcess::destroyed, syncThread, &QThread::deleteLater);
|
||||
connect(syncProcess, &SyncProcess::fileCountChanged, progWidget, &ProgressWidget::setMaximum);
|
||||
connect(syncProcess, &SyncProcess::progressStep, progWidget, &ProgressWidget::setValue);
|
||||
connect(syncProcess, &SyncProcess::progressMessage, progWidget, &ProgressWidget::addMessage);
|
||||
connect(syncProcess, &SyncProcess::statusMessage, progWidget, &ProgressWidget::setInfo);
|
||||
connect(syncProcess, &SyncProcess::started, progressDlg, &ProgressDialog::setProcessStarted);
|
||||
connect(syncProcess, &SyncProcess::finished, progressDlg, &ProgressDialog::setProcessStopped);
|
||||
connect(syncProcess, &SyncProcess::finished, [=]() { QApplication::alert(this); });
|
||||
connect(progressDlg, &ProgressDialog::rejected, syncProcess, &SyncProcess::stop);
|
||||
connect(progressDlg, &ProgressDialog::rejected, syncProcess, &SyncProcess::deleteLater);
|
||||
|
||||
// go (finally)
|
||||
syncThread->start();
|
||||
emit startSync();
|
||||
}
|
||||
|
||||
void MainWindow::changelog()
|
||||
@@ -861,7 +1122,7 @@ void MainWindow::readBackup()
|
||||
return;
|
||||
// TODO implementation
|
||||
}
|
||||
QString fileName = QFileDialog::getSaveFileName(this, tr("Save Radio Backup to File"), g.eepromDir(), tr(EXTERNAL_EEPROM_FILES_FILTER));
|
||||
QString fileName = QFileDialog::getSaveFileName(this, tr("Save Radio Backup to File"), g.eepromDir(), EXTERNAL_EEPROM_FILES_FILTER);
|
||||
if (!fileName.isEmpty()) {
|
||||
if (!readEepromFromRadio(fileName))
|
||||
return;
|
||||
@@ -870,7 +1131,7 @@ void MainWindow::readBackup()
|
||||
|
||||
void MainWindow::readFlash()
|
||||
{
|
||||
QString fileName = QFileDialog::getSaveFileName(this,tr("Read Radio Firmware to File"), g.flashDir(),tr(FLASH_FILES_FILTER));
|
||||
QString fileName = QFileDialog::getSaveFileName(this,tr("Read Radio Firmware to File"), g.flashDir(), FLASH_FILES_FILTER);
|
||||
if (!fileName.isEmpty()) {
|
||||
readFirmwareFromRadio(fileName);
|
||||
}
|
||||
|
||||
@@ -54,6 +54,7 @@ class MainWindow : public QMainWindow
|
||||
|
||||
signals:
|
||||
void firmwareChanged();
|
||||
void startSync();
|
||||
|
||||
protected:
|
||||
QString getCompanionUpdateBaseUrl();
|
||||
|
||||
@@ -1480,7 +1480,7 @@ void MdiChild::writeEeprom() // write to Tx
|
||||
|
||||
bool MdiChild::loadBackup()
|
||||
{
|
||||
QString fileName = QFileDialog::getOpenFileName(this, tr("Open backup Models and Settings file"), g.eepromDir(), tr(EEPROM_FILES_FILTER));
|
||||
QString fileName = QFileDialog::getOpenFileName(this, tr("Open backup Models and Settings file"), g.eepromDir(), EEPROM_FILES_FILTER);
|
||||
if (fileName.isEmpty())
|
||||
return false;
|
||||
QFile file(fileName);
|
||||
|
||||
@@ -41,7 +41,8 @@ ExpoDialog::ExpoDialog(QWidget *parent, ModelData & model, ExpoData *expoData, G
|
||||
cb_fp[i] = tmp[i];
|
||||
}
|
||||
|
||||
setWindowTitle(tr("Edit %1").arg(modelPrinter.printInputName(ed->chn)));
|
||||
RawSourceType srcType = (firmware->getCapability(VirtualInputs) ? SOURCE_TYPE_VIRTUAL_INPUT : SOURCE_TYPE_STICK);
|
||||
setWindowTitle(tr("Edit %1").arg(RawSource(srcType, ed->chn).toString(&model, &generalSettings)));
|
||||
QRegExp rx(CHAR_FOR_NAMES_REGEX);
|
||||
|
||||
if (IS_HORUS_OR_TARANIS(getCurrentBoard())) {
|
||||
|
||||
@@ -153,26 +153,26 @@ bool InputsPanel::AddInputLine(int dest)
|
||||
QString InputsPanel::getInputText(int dest, bool * new_ch)
|
||||
{
|
||||
QString str;
|
||||
if (new_ch) *new_ch = 0;
|
||||
|
||||
if (new_ch)
|
||||
*new_ch = false;
|
||||
|
||||
if (dest < 0) {
|
||||
str = modelPrinter.printInputName(-dest-1);
|
||||
if (new_ch) *new_ch = 1;
|
||||
if (new_ch)
|
||||
*new_ch = true;
|
||||
}
|
||||
else {
|
||||
ExpoData & input = model->expoData[dest];
|
||||
int nameChars = (firmware->getCapability(VirtualInputs) ? 10 : 4);
|
||||
|
||||
if ((dest == 0) || (model->expoData[dest-1].chn != input.chn)) {
|
||||
if (new_ch) *new_ch = 1;
|
||||
if (firmware->getCapability(VirtualInputs))
|
||||
str += QString("%1").arg(modelPrinter.printInputName(input.chn), -10, ' ');
|
||||
else
|
||||
str = modelPrinter.printInputName(input.chn);
|
||||
if (new_ch)
|
||||
*new_ch = true;
|
||||
str = QString("%1").arg(modelPrinter.printInputName(input.chn), -nameChars, QChar(' '));
|
||||
}
|
||||
else {
|
||||
if (firmware->getCapability(VirtualInputs))
|
||||
str = " ";
|
||||
else
|
||||
str = " ";
|
||||
str = QString(nameChars, QChar(' '));
|
||||
}
|
||||
str.replace(" ", " ");
|
||||
str += modelPrinter.printInputLine(input);
|
||||
|
||||
@@ -48,7 +48,7 @@ LogicalSwitchesPanel::LogicalSwitchesPanel(QWidget * parent, ModelData & model,
|
||||
// The label
|
||||
QLabel * label = new QLabel(this);
|
||||
label->setProperty("index", i);
|
||||
label->setText(tr("L%1").arg(i+1));
|
||||
label->setText(RawSwitch(SWITCH_TYPE_VIRTUAL, i+1).toString());
|
||||
label->setContextMenuPolicy(Qt::CustomContextMenu);
|
||||
label->setMouseTracking(true);
|
||||
label->setSizePolicy(QSizePolicy::Fixed, QSizePolicy::Minimum);
|
||||
|
||||
@@ -40,7 +40,7 @@ MixerDialog::MixerDialog(QWidget *parent, ModelData & model, MixData *mixdata, G
|
||||
cb_fp[i] = tmp[i];
|
||||
}
|
||||
|
||||
this->setWindowTitle(tr("DEST -> CH%1").arg(md->destCh));
|
||||
this->setWindowTitle(tr("DEST -> %1").arg(RawSource(SOURCE_TYPE_CH, md->destCh-1).toString(&model, &generalSettings)));
|
||||
|
||||
ui->sourceCB->setModel(Helpers::getRawSourceItemModel(&generalSettings, &model, POPULATE_NONE | POPULATE_SOURCES | POPULATE_SCRIPT_OUTPUTS | POPULATE_VIRTUAL_INPUTS | POPULATE_SWITCHES | POPULATE_TRIMS));
|
||||
ui->sourceCB->setCurrentIndex(ui->sourceCB->findData(md->srcRaw.toValue()));
|
||||
|
||||
@@ -51,7 +51,6 @@ TimerPanel::TimerPanel(QWidget *parent, ModelData & model, TimerData & timer, Ge
|
||||
// Mode
|
||||
ui->mode->setModel(Helpers::getRawSwitchItemModel(&generalSettings, Helpers::TimersContext));
|
||||
ui->mode->setCurrentIndex(ui->mode->findData(timer.mode.toValue()));
|
||||
//Helpers::populateSwitchCB(ui->mode, timer.mode, generalSettings, Helpers::TimersContext);
|
||||
|
||||
if (!firmware->getCapability(PermTimers)) {
|
||||
ui->persistent->hide();
|
||||
@@ -121,8 +120,11 @@ QWidget * TimerPanel::getLastFocus()
|
||||
|
||||
void TimerPanel::on_value_editingFinished()
|
||||
{
|
||||
timer.val = ui->value->time().hour()*3600 + ui->value->time().minute()*60 + ui->value->time().second();
|
||||
emit modified();
|
||||
unsigned val = ui->value->time().hour()*3600 + ui->value->time().minute()*60 + ui->value->time().second();
|
||||
if (timer.val != val) {
|
||||
timer.val = val;
|
||||
emit modified();
|
||||
}
|
||||
}
|
||||
|
||||
void TimerPanel::on_mode_currentIndexChanged(int index)
|
||||
@@ -141,9 +143,11 @@ void TimerPanel::on_minuteBeep_toggled(bool checked)
|
||||
|
||||
void TimerPanel::on_name_editingFinished()
|
||||
{
|
||||
int length = ui->name->maxLength();
|
||||
strncpy(timer.name, ui->name->text().toLatin1(), length);
|
||||
emit modified();
|
||||
if (QString(timer.name) != ui->name->text()) {
|
||||
int length = ui->name->maxLength();
|
||||
strncpy(timer.name, ui->name->text().toLatin1(), length);
|
||||
emit modified();
|
||||
}
|
||||
}
|
||||
|
||||
/******************************************************************************/
|
||||
@@ -234,15 +238,15 @@ ModulePanel::ModulePanel(QWidget * parent, ModelData & model, ModuleData & modul
|
||||
|
||||
disableMouseScrolling();
|
||||
|
||||
update();
|
||||
|
||||
connect(ui->protocol, static_cast<void(QComboBox::*)(int)>(&QComboBox::currentIndexChanged), this, &ModulePanel::onProtocolChanged);
|
||||
connect(ui->multiProtocol, static_cast<void(QComboBox::*)(int)>(&QComboBox::currentIndexChanged), this, &ModulePanel::onMultiProtocolChanged);
|
||||
connect(this, &ModulePanel::channelsRangeChanged, this, &ModulePanel::setupFailsafes);
|
||||
connect(ui->btnGrpValueType, static_cast<void(QButtonGroup::*)(int)>(&QButtonGroup::buttonClicked), this, &ModulePanel::onFailsafesDisplayValueTypeChanged);
|
||||
|
||||
lock = false;
|
||||
|
||||
// a change will not register if only one item was added
|
||||
if (ui->protocol->count() == 1) {
|
||||
on_protocol_currentIndexChanged(ui->protocol->currentIndex());
|
||||
}
|
||||
}
|
||||
|
||||
ModulePanel::~ModulePanel()
|
||||
@@ -476,7 +480,7 @@ void ModulePanel::update()
|
||||
ui->optionValue->setMinimum(pdef.getOptionMin());
|
||||
ui->optionValue->setMaximum(pdef.getOptionMax());
|
||||
ui->optionValue->setValue(module.multi.optionValue);
|
||||
ui->label_option->setText(pdef.optionsstr);
|
||||
ui->label_option->setText(qApp->translate("Multiprotocols", qPrintable(pdef.optionsstr)));
|
||||
}
|
||||
ui->multiSubType->setCurrentIndex(module.subType);
|
||||
|
||||
@@ -533,7 +537,7 @@ void ModulePanel::on_trainerMode_currentIndexChanged(int index)
|
||||
}
|
||||
}
|
||||
|
||||
void ModulePanel::on_protocol_currentIndexChanged(int index)
|
||||
void ModulePanel::onProtocolChanged(int index)
|
||||
{
|
||||
if (!lock) {
|
||||
module.protocol = ui->protocol->itemData(index).toInt();
|
||||
@@ -562,7 +566,7 @@ void ModulePanel::on_ppmOutputType_currentIndexChanged(int index)
|
||||
|
||||
void ModulePanel::on_channelsCount_editingFinished()
|
||||
{
|
||||
if (!lock) {
|
||||
if (!lock && module.channelsCount != ui->channelsCount->value()) {
|
||||
module.channelsCount = ui->channelsCount->value();
|
||||
update();
|
||||
emit channelsRangeChanged();
|
||||
@@ -572,8 +576,8 @@ void ModulePanel::on_channelsCount_editingFinished()
|
||||
|
||||
void ModulePanel::on_channelsStart_editingFinished()
|
||||
{
|
||||
if (!lock) {
|
||||
module.channelsStart = ui->channelsStart->value() - 1;
|
||||
if (!lock && module.channelsStart != (unsigned)ui->channelsStart->value() - 1) {
|
||||
module.channelsStart = (unsigned)ui->channelsStart->value() - 1;
|
||||
update();
|
||||
emit channelsRangeChanged();
|
||||
emit modified();
|
||||
@@ -582,7 +586,7 @@ void ModulePanel::on_channelsStart_editingFinished()
|
||||
|
||||
void ModulePanel::on_ppmDelay_editingFinished()
|
||||
{
|
||||
if (!lock) {
|
||||
if (!lock && module.ppm.delay != ui->ppmDelay->value()) {
|
||||
// TODO only accept valid values
|
||||
module.ppm.delay = ui->ppmDelay->value();
|
||||
emit modified();
|
||||
@@ -591,14 +595,19 @@ void ModulePanel::on_ppmDelay_editingFinished()
|
||||
|
||||
void ModulePanel::on_rxNumber_editingFinished()
|
||||
{
|
||||
module.modelId = ui->rxNumber->value();
|
||||
emit modified();
|
||||
if (module.modelId != (unsigned)ui->rxNumber->value()) {
|
||||
module.modelId = (unsigned)ui->rxNumber->value();
|
||||
emit modified();
|
||||
}
|
||||
}
|
||||
|
||||
void ModulePanel::on_ppmFrameLength_editingFinished()
|
||||
{
|
||||
module.ppm.frameLength = (ui->ppmFrameLength->value()-22.5) / 0.5;
|
||||
emit modified();
|
||||
int val = (ui->ppmFrameLength->value()-22.5) / 0.5;
|
||||
if (module.ppm.frameLength != val) {
|
||||
module.ppm.frameLength = val;
|
||||
emit modified();
|
||||
}
|
||||
}
|
||||
|
||||
void ModulePanel::on_failsafeMode_currentIndexChanged(int value)
|
||||
@@ -610,7 +619,7 @@ void ModulePanel::on_failsafeMode_currentIndexChanged(int value)
|
||||
}
|
||||
}
|
||||
|
||||
void ModulePanel::on_multiProtocol_currentIndexChanged(int index)
|
||||
void ModulePanel::onMultiProtocolChanged(int index)
|
||||
{
|
||||
if (!lock) {
|
||||
lock=true;
|
||||
@@ -627,8 +636,10 @@ void ModulePanel::on_multiProtocol_currentIndexChanged(int index)
|
||||
|
||||
void ModulePanel::on_optionValue_editingFinished()
|
||||
{
|
||||
module.multi.optionValue = ui->optionValue->value();
|
||||
emit modified();
|
||||
if (module.multi.optionValue != ui->optionValue->value()) {
|
||||
module.multi.optionValue = ui->optionValue->value();
|
||||
emit modified();
|
||||
}
|
||||
}
|
||||
|
||||
void ModulePanel::on_multiSubType_currentIndexChanged(int index)
|
||||
@@ -753,16 +764,16 @@ void ModulePanel::updateFailsafe(int channel)
|
||||
const int failsafeValue = module.failsafeChannels[channel];
|
||||
const ChannelFailsafeWidgetsGroup & grp = failsafeGroupsMap.value(channel);
|
||||
const bool valDisable = (failsafeValue == FAILSAFE_CHANNEL_HOLD || failsafeValue == FAILSAFE_CHANNEL_NOPULSE);
|
||||
const int cbIdx = (failsafeValue == FAILSAFE_CHANNEL_HOLD ? 1 : failsafeValue == FAILSAFE_CHANNEL_NOPULSE ? 2 : 0);
|
||||
|
||||
if (grp.combo)
|
||||
grp.combo->setCurrentIndex(cbIdx);
|
||||
grp.combo->setCurrentIndex(grp.combo->findData(valDisable ? failsafeValue : 0));
|
||||
if (grp.sbPercent)
|
||||
grp.sbPercent->setDisabled(valDisable);
|
||||
if (grp.sbUsec)
|
||||
grp.sbUsec->setDisabled(valDisable);
|
||||
|
||||
setChannelFailsafeValue(channel, (valDisable ? 0 : failsafeValue), (FAILSAFE_DISPLAY_PERCENT | FAILSAFE_DISPLAY_USEC));
|
||||
if (!valDisable)
|
||||
setChannelFailsafeValue(channel, failsafeValue, (FAILSAFE_DISPLAY_PERCENT | FAILSAFE_DISPLAY_USEC));
|
||||
}
|
||||
|
||||
/******************************************************************************/
|
||||
@@ -855,7 +866,7 @@ SetupPanel::SetupPanel(QWidget * parent, ModelData & model, GeneralSettings & ge
|
||||
if (i<firmware->getCapability(Timers)) {
|
||||
timers[i] = new TimerPanel(this, model, model.timers[i], generalSettings, firmware, prevFocus);
|
||||
ui->gridLayout->addWidget(timers[i], 1+i, 1);
|
||||
connect(timers[i], SIGNAL(modified()), this, SLOT(onChildModified()));
|
||||
connect(timers[i], &TimerPanel::modified, this, &SetupPanel::modified);
|
||||
prevFocus = timers[i]->getLastFocus();
|
||||
}
|
||||
else {
|
||||
@@ -987,14 +998,14 @@ SetupPanel::SetupPanel(QWidget * parent, ModelData & model, GeneralSettings & ge
|
||||
for (int i=0; i<firmware->getCapability(NumModules); i++) {
|
||||
modules[i] = new ModulePanel(this, model, model.moduleData[i], generalSettings, firmware, i);
|
||||
ui->modulesLayout->addWidget(modules[i]);
|
||||
connect(modules[i], SIGNAL(modified()), this, SLOT(onChildModified()));
|
||||
connect(modules[i], &ModulePanel::modified, this, &SetupPanel::modified);
|
||||
connect(this, &SetupPanel::extendedLimitsToggled, modules[i], &ModulePanel::onExtendedLimitsToggled);
|
||||
}
|
||||
|
||||
if (firmware->getCapability(ModelTrainerEnable)) {
|
||||
modules[CPN_MAX_MODULES] = new ModulePanel(this, model, model.moduleData[CPN_MAX_MODULES], generalSettings, firmware, -1);
|
||||
ui->modulesLayout->addWidget(modules[CPN_MAX_MODULES]);
|
||||
connect(modules[CPN_MAX_MODULES], SIGNAL(modified()), this, SLOT(onChildModified()));
|
||||
connect(modules[CPN_MAX_MODULES], &ModulePanel::modified, this, &SetupPanel::modified);
|
||||
}
|
||||
|
||||
disableMouseScrolling();
|
||||
@@ -1048,9 +1059,11 @@ void SetupPanel::on_throttleSource_currentIndexChanged(int index)
|
||||
|
||||
void SetupPanel::on_name_editingFinished()
|
||||
{
|
||||
int length = ui->name->maxLength();
|
||||
strncpy(model->name, ui->name->text().toLatin1(), length);
|
||||
emit modified();
|
||||
if (QString(model->name) != ui->name->text()) {
|
||||
int length = ui->name->maxLength();
|
||||
strncpy(model->name, ui->name->text().toLatin1(), length);
|
||||
emit modified();
|
||||
}
|
||||
}
|
||||
|
||||
void SetupPanel::on_image_currentIndexChanged(int index)
|
||||
@@ -1293,8 +1306,3 @@ void SetupPanel::onBeepCenterToggled(bool checked)
|
||||
emit modified();
|
||||
}
|
||||
}
|
||||
|
||||
void SetupPanel::onChildModified()
|
||||
{
|
||||
emit modified();
|
||||
}
|
||||
|
||||
@@ -71,7 +71,7 @@ class ModulePanel : public ModelPanel
|
||||
private slots:
|
||||
void setupFailsafes();
|
||||
void on_trainerMode_currentIndexChanged(int index);
|
||||
void on_protocol_currentIndexChanged(int index);
|
||||
void onProtocolChanged(int index);
|
||||
void on_ppmDelay_editingFinished();
|
||||
void on_channelsCount_editingFinished();
|
||||
void on_channelsStart_editingFinished();
|
||||
@@ -81,7 +81,7 @@ class ModulePanel : public ModelPanel
|
||||
void on_antennaMode_currentIndexChanged(int index);
|
||||
void on_rxNumber_editingFinished();
|
||||
void on_failsafeMode_currentIndexChanged(int value);
|
||||
void on_multiProtocol_currentIndexChanged(int index);
|
||||
void onMultiProtocolChanged(int index);
|
||||
void on_multiSubType_currentIndexChanged(int index);
|
||||
void on_autoBind_stateChanged(int state);
|
||||
void on_lowPower_stateChanged(int state);
|
||||
@@ -140,7 +140,6 @@ class SetupPanel : public ModelPanel
|
||||
void startupSwitchToggled(bool checked);
|
||||
void potWarningToggled(bool checked);
|
||||
void on_potWarningMode_currentIndexChanged(int index);
|
||||
void onChildModified();
|
||||
|
||||
private:
|
||||
Ui::Setup *ui;
|
||||
|
||||
@@ -22,6 +22,7 @@
|
||||
#include "modelprinter.h"
|
||||
#include "multiprotocols.h"
|
||||
|
||||
#include <QApplication>
|
||||
#include <QPainter>
|
||||
#include <QFile>
|
||||
#include <QUrl>
|
||||
@@ -146,7 +147,7 @@ QString ModelPrinter::printMultiSubType(int rfProtocol, bool custom, unsigned in
|
||||
Multiprotocols::MultiProtocolDefinition pdef = multiProtocols.getProtocol(rfProtocol);
|
||||
|
||||
if (subType < (unsigned int) pdef.subTypeStrings.size())
|
||||
return pdef.subTypeStrings[subType];
|
||||
return qApp->translate("Multiprotocols", qPrintable(pdef.subTypeStrings[subType]));
|
||||
else
|
||||
return "???";
|
||||
}
|
||||
@@ -327,20 +328,8 @@ QString ModelPrinter::printRotaryEncoder(int flightModeIndex, int reIndex)
|
||||
|
||||
QString ModelPrinter::printInputName(int idx)
|
||||
{
|
||||
QString result;
|
||||
if (firmware->getCapability(VirtualInputs)) {
|
||||
if (strlen(model.inputNames[idx]) > 0) {
|
||||
result = tr("[I%1]").arg(idx+1);
|
||||
result += QString(model.inputNames[idx]);
|
||||
}
|
||||
else {
|
||||
result = tr("Input%1").arg(idx+1, 2, 10, QChar('0'));
|
||||
}
|
||||
}
|
||||
else {
|
||||
result = RawSource(SOURCE_TYPE_STICK, idx).toString(&model, &generalSettings);
|
||||
}
|
||||
return result.toHtmlEscaped();
|
||||
RawSourceType srcType = (firmware->getCapability(VirtualInputs) ? SOURCE_TYPE_VIRTUAL_INPUT : SOURCE_TYPE_STICK);
|
||||
return RawSource(srcType, idx).toString(&model, &generalSettings).toHtmlEscaped();
|
||||
}
|
||||
|
||||
QString ModelPrinter::printInputLine(int idx)
|
||||
|
||||
@@ -34,7 +34,6 @@
|
||||
#define sleep(x) Sleep(x*1000)
|
||||
#else
|
||||
#include <unistd.h>
|
||||
#include "mountlist.h"
|
||||
#endif
|
||||
|
||||
FlashProcess::FlashProcess(const QString &cmd, const QStringList &args, ProgressWidget *progress):
|
||||
@@ -240,7 +239,7 @@ void FlashProcess::onReadyReadStandardError()
|
||||
void FlashProcess::errorWizard()
|
||||
{
|
||||
QString output = progress->getText();
|
||||
|
||||
|
||||
if (output.contains("avrdude: Expected signature for")) { // wrong signature
|
||||
int pos = output.indexOf("avrdude: Device signature = ");
|
||||
bool fwexist = false;
|
||||
|
||||
+212
-89
@@ -19,133 +19,256 @@
|
||||
*/
|
||||
|
||||
#include "process_sync.h"
|
||||
#include "progresswidget.h"
|
||||
#include <QDirIterator>
|
||||
|
||||
#include <QApplication>
|
||||
#include <QCryptographicHash>
|
||||
#include <QDateTime>
|
||||
#include <QMessageBox>
|
||||
#include <QTextStream>
|
||||
#include <QMutexLocker>
|
||||
#include <QDirIterator>
|
||||
#include <QDebug>
|
||||
#include <QEventLoop>
|
||||
#include <QTimer>
|
||||
|
||||
SyncProcess::SyncProcess(const QString & folder1, const QString & folder2, ProgressWidget * progress):
|
||||
folder1(folder1),
|
||||
folder2(folder2),
|
||||
progress(progress),
|
||||
index(0),
|
||||
count(0),
|
||||
closed(false)
|
||||
#if (QT_VERSION < QT_VERSION_CHECK(5, 5, 0))
|
||||
#define QtInfoMsg QtMsgType(4)
|
||||
#endif
|
||||
|
||||
#define PRINT_INFO(str) emit progressMessage((str), QtInfoMsg)
|
||||
#define PRINT_CREATE(str) emit progressMessage((str), QtInfoMsg)
|
||||
#define PRINT_REPLACE(str) emit progressMessage((str), QtWarningMsg)
|
||||
#define PRINT_DELETE(str) emit progressMessage((str), QtCriticalMsg)
|
||||
#define PRINT_ERROR(str) emit progressMessage((str), QtFatalMsg)
|
||||
//#define PRINT_SKIP(str) emit progressMessage((str), QtDebugMsg) // mostly useless noise (maybe make an option later)
|
||||
#define PRINT_SKIP(str)
|
||||
#define PRINT_SEP() PRINT_INFO(QString(80, '='))
|
||||
|
||||
#define SYNC_MAX_ERRORS 50 // give up after this many errors per destination
|
||||
|
||||
SyncProcess::SyncProcess(const QString & folderA, const QString & folderB, const int & syncDirection, const int & compareType, const qint64 & maxFileSize, const bool dryRun):
|
||||
folder1(folderA),
|
||||
folder2(folderB),
|
||||
direction((SyncDirection)syncDirection),
|
||||
ctype((SyncCompareType)compareType),
|
||||
maxFileSize(qMax<qint64>(0, maxFileSize)),
|
||||
dryRun(dryRun),
|
||||
stopping(false)
|
||||
{
|
||||
connect(progress, SIGNAL(stopped()),this, SLOT(onClosed()));
|
||||
if (direction == SYNC_B2A_A2B) {
|
||||
folder1 = folderB;
|
||||
folder2 = folderA;
|
||||
direction = SYNC_A2B_B2A;
|
||||
}
|
||||
|
||||
if (ctype == OVERWR_ALWAYS && direction == SYNC_A2B_B2A)
|
||||
ctype = OVERWR_IF_DIFF;
|
||||
|
||||
dirFilters = QDir::Filters(QDir::AllDirs | QDir::Files | QDir::NoDotAndDotDot);
|
||||
|
||||
reportTemplate = tr("New: <b>%1</b>; Updated: <b>%2</b>; Skipped: <b>%3</b>; Errors: <font color=%5><b>%4</b></font>;");
|
||||
if (dryRun)
|
||||
testRunStr = tr("[TEST RUN] ");
|
||||
}
|
||||
|
||||
void SyncProcess::onClosed()
|
||||
void SyncProcess::stop()
|
||||
{
|
||||
closed = true;
|
||||
QMutexLocker locker(&stopReqMutex);
|
||||
stopping = true;
|
||||
}
|
||||
|
||||
bool SyncProcess::run()
|
||||
bool SyncProcess::isStopRequsted()
|
||||
{
|
||||
if (!QFile::exists(folder1)) {
|
||||
QMessageBox::warning(NULL, QObject::tr("Synchronization error"), QObject::tr("The directory '%1' doesn't exist!").arg(folder1));
|
||||
return true;
|
||||
QMutexLocker locker(&stopReqMutex);
|
||||
return stopping;
|
||||
}
|
||||
|
||||
void SyncProcess::run()
|
||||
{
|
||||
count = index = created = updated = skipped = errored = 0;
|
||||
|
||||
emit started();
|
||||
emit progressStep(index);
|
||||
emit statusMessage(tr("Gathering file information..."));
|
||||
|
||||
if (direction == SYNC_A2B_B2A || direction == SYNC_A2B)
|
||||
count += getFilesCount(folder1);
|
||||
|
||||
if (isStopRequsted()) {
|
||||
finish();
|
||||
return;
|
||||
}
|
||||
|
||||
if (!QFile::exists(folder2)) {
|
||||
QMessageBox::warning(NULL, QObject::tr("Synchronization error"), QObject::tr("The directory '%1' doesn't exist!").arg(folder2));
|
||||
return true;
|
||||
if (direction == SYNC_A2B_B2A || direction == SYNC_B2A)
|
||||
count += getFilesCount(folder2);
|
||||
|
||||
if (isStopRequsted()) {
|
||||
finish();
|
||||
return;
|
||||
}
|
||||
|
||||
count = getFilesCount(folder1) + getFilesCount(folder2);
|
||||
progress->setMaximum(count);
|
||||
emit fileCountChanged(count);
|
||||
|
||||
QStringList errors = updateDir(folder1, folder2) + updateDir(folder2, folder1);
|
||||
if (errors.count() > 0) {
|
||||
QMessageBox::warning(NULL, QObject::tr("Synchronization error"), errors.join("\n"));
|
||||
if (!count) {
|
||||
QString nf = tr("Synchronization failed, nothing found to copy.");
|
||||
emit statusMessage(nf);
|
||||
PRINT_ERROR(nf);
|
||||
emit finished();
|
||||
return;
|
||||
}
|
||||
|
||||
// don't close the window unless the user wanted
|
||||
return closed;
|
||||
if (direction == SYNC_A2B_B2A || direction == SYNC_A2B)
|
||||
updateDir(folder1, folder2);
|
||||
|
||||
if (isStopRequsted()) {
|
||||
finish();
|
||||
return;
|
||||
}
|
||||
|
||||
if (direction == SYNC_A2B_B2A || direction == SYNC_B2A)
|
||||
updateDir(folder2, folder1);
|
||||
|
||||
finish();
|
||||
}
|
||||
|
||||
void SyncProcess::finish()
|
||||
{
|
||||
QString endStr = testRunStr % tr("Synchronization finished. ") % reportTemplate;
|
||||
emit statusMessage(endStr.arg(created).arg(updated).arg(skipped).arg(errored).arg(errored ? "red" : "black"));
|
||||
emit finished();
|
||||
}
|
||||
|
||||
int SyncProcess::getFilesCount(const QString & directory)
|
||||
{
|
||||
if (!QFile::exists(directory))
|
||||
return 0;
|
||||
|
||||
int result = 0;
|
||||
QDirIterator it(directory, QDirIterator::Subdirectories);
|
||||
while (it.hasNext()) {
|
||||
QDirIterator it(directory, dirFilters, QDirIterator::Subdirectories | QDirIterator::FollowSymlinks);
|
||||
while (it.hasNext() && !isStopRequsted()) {
|
||||
it.next();
|
||||
result++;
|
||||
QApplication::processEvents();
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
QStringList SyncProcess::updateDir(const QString & source, const QString & destination)
|
||||
void SyncProcess::updateDir(const QString & source, const QString & destination)
|
||||
{
|
||||
QDirIterator it(source, QDirIterator::Subdirectories);
|
||||
while (!closed && it.hasNext()) {
|
||||
QEventLoop loop;
|
||||
QTimer::singleShot(10, &loop, SLOT(quit()));
|
||||
loop.exec();
|
||||
index++;
|
||||
progress->setInfo(tr("%1/%2 files").arg(index).arg(count));
|
||||
progress->setValue(index);
|
||||
QString result = updateEntry(it.next(), source, destination);
|
||||
if (!result.isEmpty()) {
|
||||
errors << result;
|
||||
int counts[4] = { created, updated, skipped, errored };
|
||||
QString statusStr = testRunStr % tr("Synchronizing %1 -> %2: %3").arg(source, destination, "<b>%1</b>|<b>%2</b> (%3)");
|
||||
|
||||
PRINT_INFO(testRunStr % tr("Starting synchronization: %1 -> %2<br>").arg(source, destination));
|
||||
|
||||
QDirIterator it(source, dirFilters, QDirIterator::Subdirectories | QDirIterator::FollowSymlinks);
|
||||
while (it.hasNext() && !isStopRequsted()) {
|
||||
it.next();
|
||||
++index;
|
||||
emit statusMessage(statusStr.arg(index).arg(count).arg(reportTemplate.arg(created).arg(updated).arg(skipped).arg(errored).arg(errored ? "red" : "black")));
|
||||
emit progressStep(index);
|
||||
if (maxFileSize && it.fileInfo().isFile() && it.fileInfo().size() > maxFileSize) {
|
||||
PRINT_SKIP(tr("Skipping large file: %1 (%2KB)").arg(it.fileName()).arg(int(it.fileInfo().size() / 1024)));
|
||||
++skipped;
|
||||
}
|
||||
else {
|
||||
updateEntry(it.filePath(), source, destination);
|
||||
if (errored - counts[3] > SYNC_MAX_ERRORS) {
|
||||
PRINT_ERROR(tr("<br><b>Too many errors, giving up.<b>"));
|
||||
break;
|
||||
}
|
||||
}
|
||||
QApplication::processEvents();
|
||||
}
|
||||
return errors;
|
||||
|
||||
QString endStr = "<br>" % testRunStr % tr("Finished synchronizing %1 -> %2 :<br> %3").arg(source, destination, reportTemplate);
|
||||
PRINT_INFO(endStr.arg(created-counts[0]).arg(updated-counts[1]).arg(skipped-counts[2]).arg(errored-counts[3]).arg(errored-counts[3] ? "red" : "black"));
|
||||
PRINT_SEP();
|
||||
}
|
||||
|
||||
QString SyncProcess::updateEntry(const QString & path, const QDir & source, const QDir & destination)
|
||||
bool SyncProcess::updateEntry(const QString & entry, const QDir & source, const QDir & destination)
|
||||
{
|
||||
QFileInfo sourceInfo(path);
|
||||
QString relativePath = source.relativeFilePath(path);
|
||||
QString destinationPath = destination.absoluteFilePath(relativePath);
|
||||
QFileInfo destinationInfo(destinationPath);
|
||||
QString srcPath = source.toNativeSeparators(source.absoluteFilePath(entry));
|
||||
QString relPath = source.relativeFilePath(entry);
|
||||
QString destPath = destination.toNativeSeparators(destination.absoluteFilePath(relPath));
|
||||
QFileInfo sourceInfo(srcPath);
|
||||
QFileInfo destInfo(destPath);
|
||||
|
||||
if (sourceInfo.isDir()) {
|
||||
if (!destinationInfo.exists()) {
|
||||
progress->addText(tr("Create directory %1\n").arg(destinationPath));
|
||||
if (!destination.mkdir(relativePath)) {
|
||||
return QObject::tr("Create '%1' failed").arg(destinationPath);
|
||||
if (!destInfo.exists()) {
|
||||
PRINT_CREATE(tr("Creating directory: %1").arg(destPath));
|
||||
if (!dryRun && !destination.mkpath(destPath)) {
|
||||
PRINT_ERROR(tr("Could not create directory: %1").arg(destPath));
|
||||
++errored;
|
||||
return false;
|
||||
}
|
||||
++created;
|
||||
}
|
||||
else {
|
||||
PRINT_SKIP(tr("Destination directory exists: %1").arg(destPath));
|
||||
++skipped;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
else {
|
||||
if (!destinationInfo.exists()) {
|
||||
// qDebug() << "Copy" << path << "to" << destinationPath;
|
||||
progress->addText(tr("Copy %1 to %2").arg(path).arg(destinationPath) + "\n");
|
||||
if (!QFile::copy(path, destinationPath)) {
|
||||
return QObject::tr("Copy '%1' to '%2' failed").arg(path).arg(destinationPath);
|
||||
}
|
||||
}
|
||||
else if (sourceInfo.lastModified() > destinationInfo.lastModified()) {
|
||||
// retrieve source contents
|
||||
QFile sourceFile(path);
|
||||
if (!sourceFile.open(QFile::ReadOnly)) {
|
||||
return QObject::tr("Open '%1' failed").arg(path);
|
||||
}
|
||||
QString sourceContents = sourceFile.readAll();
|
||||
sourceFile.close();
|
||||
// try to retrieve destination contents
|
||||
QFile destinationFile(destinationPath);
|
||||
if (destinationFile.open(QFile::ReadOnly)) {
|
||||
QString destinationContents = destinationFile.readAll();
|
||||
destinationFile.close();
|
||||
if (sourceContents == destinationContents) {
|
||||
// qDebug() << "Skip" << path;
|
||||
return QString();
|
||||
}
|
||||
}
|
||||
if (!destinationFile.open(QFile::WriteOnly)) {
|
||||
return QObject::tr("Write '%1' failed").arg(destinationPath);
|
||||
}
|
||||
progress->addText(tr("Write %1").arg(destinationPath) + "\n");
|
||||
// qDebug() << "Write" << destinationPath;
|
||||
QTextStream destinationStream(&destinationFile);
|
||||
destinationStream << sourceContents;
|
||||
destinationFile.close();
|
||||
|
||||
QFile sourceFile(srcPath);
|
||||
QFile destinationFile(destPath);
|
||||
bool destExists = destInfo.exists();
|
||||
bool checkDate = (ctype == OVERWR_NEWER_IF_DIFF || ctype == OVERWR_NEWER_ALWAYS);
|
||||
bool checkContent = (ctype == OVERWR_NEWER_IF_DIFF || ctype == OVERWR_IF_DIFF);
|
||||
bool existed = false;
|
||||
|
||||
if (destExists && checkDate) {
|
||||
if (sourceInfo.lastModified() <= destInfo.lastModified()) {
|
||||
PRINT_SKIP(tr("Skipping older file: %1").arg(srcPath));
|
||||
++skipped;
|
||||
return true;
|
||||
}
|
||||
checkDate = false;
|
||||
}
|
||||
return QString();
|
||||
|
||||
if (destExists && checkContent) {
|
||||
if (!sourceFile.open(QFile::ReadOnly)) {
|
||||
PRINT_ERROR(tr("Could not open source file '%1': %2").arg(srcPath, sourceFile.errorString()));
|
||||
++errored;
|
||||
return false;
|
||||
}
|
||||
if (!destinationFile.open(QFile::ReadOnly)) {
|
||||
PRINT_ERROR(tr("Could not open destination file '%1': %2").arg(destPath, destinationFile.errorString()));
|
||||
++errored;
|
||||
return false;
|
||||
}
|
||||
|
||||
bool skip = QCryptographicHash::hash(sourceFile.readAll(), QCryptographicHash::Md5) == QCryptographicHash::hash(destinationFile.readAll(), QCryptographicHash::Md5);
|
||||
sourceFile.close();
|
||||
destinationFile.close();
|
||||
if (skip) {
|
||||
PRINT_SKIP(tr("Skipping identical file: %1").arg(srcPath));
|
||||
++skipped;
|
||||
return true;
|
||||
}
|
||||
checkContent = false;
|
||||
}
|
||||
|
||||
if (!destExists || (!checkDate && !checkContent)) {
|
||||
if (destInfo.exists()) {
|
||||
existed = true;
|
||||
PRINT_REPLACE(tr("Replacing destination file: %1").arg(destPath));
|
||||
if (!dryRun && !destinationFile.remove()) {
|
||||
PRINT_ERROR(tr("Could not delete destination file '%1': %2").arg(destPath, destinationFile.errorString()));
|
||||
++errored;
|
||||
return false;
|
||||
}
|
||||
}
|
||||
else {
|
||||
PRINT_CREATE(tr("Creating destination file: %1").arg(destPath));
|
||||
}
|
||||
if (!dryRun && !sourceFile.copy(destPath)) {
|
||||
PRINT_ERROR(tr("Copy failed: '%1' to '%2': %3").arg(srcPath, destPath, sourceFile.errorString()));
|
||||
++errored;
|
||||
return false;
|
||||
}
|
||||
|
||||
if (existed)
|
||||
++updated;
|
||||
else
|
||||
++created;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -22,34 +22,72 @@
|
||||
#define _PROCESS_SYNC_H_
|
||||
|
||||
#include <QObject>
|
||||
#include <QDir>
|
||||
#include <QMutex>
|
||||
#include <QString>
|
||||
#include <QStringList>
|
||||
|
||||
class QDir;
|
||||
class ProgressWidget;
|
||||
|
||||
class SyncProcess : public QObject
|
||||
{
|
||||
Q_OBJECT
|
||||
|
||||
public:
|
||||
SyncProcess(const QString & folder1, const QString & folder2, ProgressWidget * progress);
|
||||
bool run();
|
||||
enum SyncDirection {
|
||||
SYNC_A2B_B2A,
|
||||
SYNC_B2A_A2B,
|
||||
SYNC_A2B,
|
||||
SYNC_B2A
|
||||
};
|
||||
|
||||
protected slots:
|
||||
void onClosed();
|
||||
enum SyncCompareType {
|
||||
OVERWR_NEWER_IF_DIFF,
|
||||
OVERWR_NEWER_ALWAYS,
|
||||
OVERWR_IF_DIFF,
|
||||
OVERWR_ALWAYS
|
||||
};
|
||||
|
||||
SyncProcess(const QString & folderA,
|
||||
const QString & folderB,
|
||||
const int & syncDirection = SYNC_A2B_B2A,
|
||||
const int & compareType = OVERWR_NEWER_IF_DIFF,
|
||||
const qint64 & maxFileSize = 5*1024*1024,
|
||||
const bool dryRun = false);
|
||||
|
||||
public slots:
|
||||
void run();
|
||||
void stop();
|
||||
|
||||
signals:
|
||||
void started();
|
||||
void finished();
|
||||
void fileCountChanged(int count);
|
||||
void progressStep(int step);
|
||||
void progressMessage(const QString & text, const int & type);
|
||||
void statusMessage(const QString & text);
|
||||
|
||||
protected:
|
||||
bool isStopRequsted();
|
||||
void finish();
|
||||
int getFilesCount(const QString & directory);
|
||||
QStringList updateDir(const QString & source, const QString & destination);
|
||||
QString updateEntry(const QString & path, const QDir & source, const QDir & destination);
|
||||
void updateDir(const QString & source, const QString & destination);
|
||||
bool updateEntry(const QString & entry, const QDir & source, const QDir & destination);
|
||||
|
||||
QString folder1;
|
||||
QString folder2;
|
||||
ProgressWidget * progress;
|
||||
QStringList errors;
|
||||
SyncDirection direction;
|
||||
SyncCompareType ctype;
|
||||
qint64 maxFileSize; // Bytes
|
||||
QDir::Filters dirFilters;
|
||||
QMutex stopReqMutex;
|
||||
QString reportTemplate;
|
||||
QString testRunStr;
|
||||
int index;
|
||||
int count;
|
||||
bool closed;
|
||||
int created;
|
||||
int updated;
|
||||
int skipped;
|
||||
int errored;
|
||||
bool dryRun;
|
||||
bool stopping;
|
||||
};
|
||||
|
||||
#endif // _PROCESS_SYNC_H_
|
||||
|
||||
@@ -32,6 +32,7 @@ locked(false)
|
||||
ui->setupUi(this);
|
||||
setWindowTitle(title);
|
||||
setWindowIcon(icon);
|
||||
setWindowFlags(windowFlags() & ~Qt::WindowContextHelpButtonHint);
|
||||
if (forceOpen) {
|
||||
ui->outputProgress->forceOpen();
|
||||
}
|
||||
@@ -53,6 +54,7 @@ void ProgressDialog::on_closeButton_clicked()
|
||||
{
|
||||
if (!locked) {
|
||||
ui->outputProgress->stop();
|
||||
emit rejected();
|
||||
close();
|
||||
}
|
||||
}
|
||||
@@ -77,3 +79,13 @@ bool ProgressDialog::isEmpty() const
|
||||
{
|
||||
return ui->outputProgress->isEmpty();
|
||||
}
|
||||
|
||||
void ProgressDialog::setProcessStarted()
|
||||
{
|
||||
ui->closeButton->setText(tr("Cancel"));
|
||||
}
|
||||
|
||||
void ProgressDialog::setProcessStopped()
|
||||
{
|
||||
ui->closeButton->setText(tr("Close"));
|
||||
}
|
||||
|
||||
@@ -41,6 +41,10 @@ public:
|
||||
ProgressWidget * progress();
|
||||
bool isEmpty() const;
|
||||
|
||||
public slots:
|
||||
void setProcessStarted();
|
||||
void setProcessStopped();
|
||||
|
||||
private slots:
|
||||
void on_closeButton_clicked();
|
||||
void on_outputProgress_detailsToggled();
|
||||
|
||||
@@ -6,22 +6,16 @@
|
||||
<rect>
|
||||
<x>0</x>
|
||||
<y>0</y>
|
||||
<width>431</width>
|
||||
<height>115</height>
|
||||
<width>646</width>
|
||||
<height>211</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="MinimumExpanding" vsizetype="Minimum">
|
||||
<sizepolicy hsizetype="Preferred" vsizetype="Maximum">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="minimumSize">
|
||||
<size>
|
||||
<width>0</width>
|
||||
<height>0</height>
|
||||
</size>
|
||||
</property>
|
||||
<property name="windowTitle">
|
||||
<string>Flash Firmware</string>
|
||||
</property>
|
||||
@@ -29,28 +23,37 @@
|
||||
<iconset resource="companion.qrc">
|
||||
<normaloff>:/icon.png</normaloff>:/icon.png</iconset>
|
||||
</property>
|
||||
<property name="modal">
|
||||
<bool>true</bool>
|
||||
</property>
|
||||
<layout class="QVBoxLayout" name="verticalLayout_2">
|
||||
<layout class="QVBoxLayout" name="verticalLayout_2" stretch="1,0">
|
||||
<property name="spacing">
|
||||
<number>5</number>
|
||||
</property>
|
||||
<property name="leftMargin">
|
||||
<number>7</number>
|
||||
</property>
|
||||
<property name="topMargin">
|
||||
<number>5</number>
|
||||
</property>
|
||||
<property name="rightMargin">
|
||||
<number>7</number>
|
||||
</property>
|
||||
<property name="bottomMargin">
|
||||
<number>4</number>
|
||||
</property>
|
||||
<item>
|
||||
<widget class="ProgressWidget" name="outputProgress" native="true"/>
|
||||
</item>
|
||||
<item>
|
||||
<spacer name="spacer2">
|
||||
<property name="orientation">
|
||||
<enum>Qt::Vertical</enum>
|
||||
<widget class="ProgressWidget" name="outputProgress" native="true">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Expanding" vsizetype="Minimum">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="sizeHint" stdset="0">
|
||||
<size>
|
||||
<width>20</width>
|
||||
<height>0</height>
|
||||
</size>
|
||||
</property>
|
||||
</spacer>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<layout class="QHBoxLayout" name="horizontalLayout">
|
||||
<property name="spacing">
|
||||
<number>6</number>
|
||||
</property>
|
||||
<item>
|
||||
<spacer name="spacer1">
|
||||
<property name="orientation">
|
||||
@@ -59,7 +62,7 @@
|
||||
<property name="sizeHint" stdset="0">
|
||||
<size>
|
||||
<width>40</width>
|
||||
<height>20</height>
|
||||
<height>1</height>
|
||||
</size>
|
||||
</property>
|
||||
</spacer>
|
||||
|
||||
@@ -34,14 +34,15 @@ ui(new Ui::ProgressWidget)
|
||||
ui->checkBox->hide();
|
||||
ui->textEdit->hide();
|
||||
|
||||
QFont newFont(ui->textEdit->font());
|
||||
newFont.setFamily("Courier");
|
||||
#ifdef __APPLE__
|
||||
QFont newFont("Courier", 13);
|
||||
ui->textEdit->setFont(newFont);
|
||||
newFont.setPointSize(13);
|
||||
ui->textEdit->setAttribute(Qt::WA_MacNormalSize);
|
||||
#elif defined WIN32 || !defined __GNUC__
|
||||
QFont newFont("Courier", 9);
|
||||
ui->textEdit->setFont(newFont);
|
||||
newFont.setPointSize(9);
|
||||
#endif
|
||||
ui->textEdit->setFont(newFont);
|
||||
}
|
||||
|
||||
ProgressWidget::~ProgressWidget()
|
||||
@@ -81,14 +82,10 @@ void ProgressWidget::setValue(int value)
|
||||
ui->progressBar->setValue(value);
|
||||
}
|
||||
|
||||
void ProgressWidget::addText(const QString &text)
|
||||
void ProgressWidget::addText(const QString &text, const bool richText)
|
||||
{
|
||||
ui->checkBox->setVisible(true);
|
||||
|
||||
if (g.outputDisplayDetails()) {
|
||||
ui->checkBox->setChecked(true);
|
||||
ui->textEdit->setVisible(true);
|
||||
}
|
||||
ui->checkBox->setChecked(g.outputDisplayDetails());
|
||||
|
||||
QTextCursor cursor(ui->textEdit->textCursor());
|
||||
|
||||
@@ -96,13 +93,51 @@ void ProgressWidget::addText(const QString &text)
|
||||
bool atEnd = (ui->textEdit->verticalScrollBar()->value() == ui->textEdit->verticalScrollBar()->maximum());
|
||||
|
||||
cursor.movePosition(QTextCursor::End, QTextCursor::MoveAnchor, 1);
|
||||
cursor.insertText(text);
|
||||
if (richText)
|
||||
cursor.insertHtml(text);
|
||||
else
|
||||
cursor.insertText(text);
|
||||
|
||||
if (atEnd) {
|
||||
ui->textEdit->verticalScrollBar()->triggerAction(QAbstractSlider::SliderToMaximum);
|
||||
}
|
||||
}
|
||||
|
||||
void ProgressWidget::addHtml(const QString & text)
|
||||
{
|
||||
addText(text, true);
|
||||
}
|
||||
|
||||
void ProgressWidget::addMessage(const QString & text, const int & type)
|
||||
{
|
||||
QString color;
|
||||
switch (type) {
|
||||
case QtDebugMsg:
|
||||
color = "dimgrey"; // not important messages, may be filtered out
|
||||
break;
|
||||
case QtWarningMsg: // use warning level as emphasis
|
||||
color = "darkblue";
|
||||
break;
|
||||
case QtCriticalMsg: // use critical as a warning
|
||||
color = "#ff7900";
|
||||
break;
|
||||
case QtFatalMsg: // fatal for hard errors
|
||||
color = "red";
|
||||
break;
|
||||
case QtInfoMsg: // default plain text
|
||||
default:
|
||||
break;
|
||||
}
|
||||
if (color.isEmpty()) {
|
||||
if (text.contains(QRegExp("<[^>]+>"))) // detect html (rouhgly)
|
||||
addHtml(text % "<br>");
|
||||
else
|
||||
addText(text % "\n", false);
|
||||
}
|
||||
else
|
||||
addHtml(QString("<font color=%1>").arg(color) % text % "</font><br>");
|
||||
}
|
||||
|
||||
QString ProgressWidget::getText()
|
||||
{
|
||||
return ui->textEdit->toPlainText();
|
||||
|
||||
@@ -23,6 +23,10 @@
|
||||
|
||||
#include <QWidget>
|
||||
|
||||
#if (QT_VERSION < QT_VERSION_CHECK(5, 5, 0))
|
||||
#define QtInfoMsg QtMsgType(4)
|
||||
#endif
|
||||
|
||||
namespace Ui {
|
||||
class ProgressWidget;
|
||||
}
|
||||
@@ -35,7 +39,9 @@ class ProgressWidget : public QWidget
|
||||
explicit ProgressWidget(QWidget *parent);
|
||||
~ProgressWidget();
|
||||
void lock(bool lock);
|
||||
void addText(const QString &text);
|
||||
void addText(const QString &text, const bool richText = false);
|
||||
void addHtml(const QString &text);
|
||||
void addMessage(const QString & text, const int & type = QtInfoMsg);
|
||||
QString getText();
|
||||
void setInfo(const QString &text);
|
||||
void setMaximum(int value);
|
||||
|
||||
@@ -9,26 +9,26 @@
|
||||
<rect>
|
||||
<x>0</x>
|
||||
<y>0</y>
|
||||
<width>700</width>
|
||||
<height>244</height>
|
||||
<width>753</width>
|
||||
<height>474</height>
|
||||
</rect>
|
||||
</property>
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Preferred" vsizetype="Minimum">
|
||||
<sizepolicy hsizetype="Expanding" vsizetype="Expanding">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="minimumSize">
|
||||
<size>
|
||||
<width>700</width>
|
||||
<width>650</width>
|
||||
<height>0</height>
|
||||
</size>
|
||||
</property>
|
||||
<property name="windowTitle">
|
||||
<string>Form</string>
|
||||
</property>
|
||||
<layout class="QVBoxLayout" name="verticalLayout">
|
||||
<layout class="QVBoxLayout" name="verticalLayout" stretch="0,0,1,0">
|
||||
<property name="spacing">
|
||||
<number>6</number>
|
||||
</property>
|
||||
<property name="leftMargin">
|
||||
<number>0</number>
|
||||
</property>
|
||||
@@ -43,56 +43,79 @@
|
||||
</property>
|
||||
<item>
|
||||
<widget class="QLabel" name="info">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Preferred" vsizetype="Maximum">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="text">
|
||||
<string/>
|
||||
<string notr="true"/>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<layout class="QHBoxLayout" name="horizontalLayout" stretch="1,0">
|
||||
<item>
|
||||
<widget class="QProgressBar" name="progressBar">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Preferred" vsizetype="Preferred">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="minimumSize">
|
||||
<size>
|
||||
<width>0</width>
|
||||
<height>0</height>
|
||||
</size>
|
||||
</property>
|
||||
<property name="value">
|
||||
<number>0</number>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QCheckBox" name="checkBox">
|
||||
<property name="text">
|
||||
<string>Show Details</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
</layout>
|
||||
<widget class="QWidget" name="widget" native="true">
|
||||
<layout class="QHBoxLayout" name="horizontalLayout" stretch="1,0">
|
||||
<property name="spacing">
|
||||
<number>6</number>
|
||||
</property>
|
||||
<property name="leftMargin">
|
||||
<number>0</number>
|
||||
</property>
|
||||
<property name="topMargin">
|
||||
<number>0</number>
|
||||
</property>
|
||||
<property name="rightMargin">
|
||||
<number>0</number>
|
||||
</property>
|
||||
<property name="bottomMargin">
|
||||
<number>0</number>
|
||||
</property>
|
||||
<item>
|
||||
<widget class="QProgressBar" name="progressBar">
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Preferred" vsizetype="Maximum">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="minimumSize">
|
||||
<size>
|
||||
<width>0</width>
|
||||
<height>0</height>
|
||||
</size>
|
||||
</property>
|
||||
<property name="value">
|
||||
<number>0</number>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QCheckBox" name="checkBox">
|
||||
<property name="text">
|
||||
<string>Show Details</string>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
</layout>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<widget class="QPlainTextEdit" name="textEdit">
|
||||
<widget class="QTextEdit" name="textEdit">
|
||||
<property name="enabled">
|
||||
<bool>true</bool>
|
||||
</property>
|
||||
<property name="sizePolicy">
|
||||
<sizepolicy hsizetype="Preferred" vsizetype="Preferred">
|
||||
<sizepolicy hsizetype="Expanding" vsizetype="Expanding">
|
||||
<horstretch>0</horstretch>
|
||||
<verstretch>0</verstretch>
|
||||
</sizepolicy>
|
||||
</property>
|
||||
<property name="minimumSize">
|
||||
<size>
|
||||
<width>600</width>
|
||||
<height>100</height>
|
||||
<width>0</width>
|
||||
<height>350</height>
|
||||
</size>
|
||||
</property>
|
||||
<property name="font">
|
||||
@@ -101,32 +124,40 @@
|
||||
<pointsize>10</pointsize>
|
||||
</font>
|
||||
</property>
|
||||
<property name="lineWidth">
|
||||
<number>80</number>
|
||||
</property>
|
||||
<property name="midLineWidth">
|
||||
<number>80</number>
|
||||
</property>
|
||||
<property name="verticalScrollBarPolicy">
|
||||
<enum>Qt::ScrollBarAlwaysOn</enum>
|
||||
</property>
|
||||
<property name="horizontalScrollBarPolicy">
|
||||
<enum>Qt::ScrollBarAsNeeded</enum>
|
||||
</property>
|
||||
<property name="lineWrapMode">
|
||||
<enum>QPlainTextEdit::NoWrap</enum>
|
||||
<property name="undoRedoEnabled">
|
||||
<bool>false</bool>
|
||||
</property>
|
||||
<property name="readOnly">
|
||||
<bool>true</bool>
|
||||
</property>
|
||||
<property name="plainText">
|
||||
<string/>
|
||||
<property name="html">
|
||||
<string notr="true"><!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:'Courier'; font-size:10pt; font-weight:400; font-style:normal;">
|
||||
<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;"><br /></p></body></html></string>
|
||||
</property>
|
||||
<property name="textInteractionFlags">
|
||||
<set>Qt::TextSelectableByMouse</set>
|
||||
<set>Qt::LinksAccessibleByKeyboard|Qt::LinksAccessibleByMouse|Qt::TextBrowserInteraction|Qt::TextSelectableByKeyboard|Qt::TextSelectableByMouse</set>
|
||||
</property>
|
||||
</widget>
|
||||
</item>
|
||||
<item>
|
||||
<spacer name="verticalSpacer">
|
||||
<property name="orientation">
|
||||
<enum>Qt::Vertical</enum>
|
||||
</property>
|
||||
<property name="sizeHint" stdset="0">
|
||||
<size>
|
||||
<width>20</width>
|
||||
<height>0</height>
|
||||
</size>
|
||||
</property>
|
||||
</spacer>
|
||||
</item>
|
||||
</layout>
|
||||
</widget>
|
||||
<resources/>
|
||||
|
||||
@@ -25,15 +25,10 @@
|
||||
#include "radionotfound.h"
|
||||
#include "burnconfigdialog.h"
|
||||
#include "helpers.h"
|
||||
#include "mountlist.h"
|
||||
#include "process_copy.h"
|
||||
#include "storage.h"
|
||||
#include "progresswidget.h"
|
||||
|
||||
#if defined WIN32 || !defined __GNUC__
|
||||
#include <windows.h>
|
||||
#endif
|
||||
|
||||
QString getRadioInterfaceCmd()
|
||||
{
|
||||
burnConfigDialog bcd;
|
||||
@@ -401,7 +396,9 @@ bool writeEeprom(const QString & filename, ProgressWidget * progress)
|
||||
return false;
|
||||
}
|
||||
|
||||
#if (QT_VERSION < QT_VERSION_CHECK(5, 4, 0))
|
||||
#if defined WIN32 || !defined __GNUC__
|
||||
#include <windows.h>
|
||||
bool isRemovableMedia(const QString & vol)
|
||||
{
|
||||
char szDosDeviceName[MAX_PATH];
|
||||
@@ -415,61 +412,69 @@ bool isRemovableMedia(const QString & vol)
|
||||
}
|
||||
return true;
|
||||
}
|
||||
#endif
|
||||
#else
|
||||
#include "mountlist.h"
|
||||
#endif // defined WIN32 || !defined __GNUC__
|
||||
#endif // (QT_VERSION < QT_VERSION_CHECK(5, 4, 0))
|
||||
|
||||
QString findMassstoragePath(const QString & filename, bool onlyPath)
|
||||
{
|
||||
QString temppath;
|
||||
QStringList drives;
|
||||
QString eepromfile;
|
||||
QString fsname;
|
||||
bool found = false;
|
||||
QRegularExpression fstypeRe("^(v?fat|msdos)", QRegularExpression::CaseInsensitiveOption); // Linux: "vfat"; macOS: "msdos"; Win: "FAT32"
|
||||
#if (QT_VERSION >= QT_VERSION_CHECK(5, 4, 0))
|
||||
foreach(const QStorageInfo & si, QStorageInfo::mountedVolumes()) {
|
||||
//qDebug() << si.rootPath() << si.name() << si.device() << si.displayName() << si.fileSystemType() << si.isReady();
|
||||
if (!si.isReady() || !QString(si.fileSystemType()).contains(fstypeRe))
|
||||
continue;
|
||||
temppath = si.rootPath();
|
||||
eepromfile = temppath % "/" % filename;
|
||||
qDebug() << "Searching for" << eepromfile;
|
||||
if (QFile::exists(eepromfile)) {
|
||||
found = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
#elif defined WIN32 || !defined __GNUC__
|
||||
static QStringList blacklist;
|
||||
|
||||
#if defined WIN32 || !defined __GNUC__
|
||||
foreach(QFileInfo drive, QDir::drives()) {
|
||||
foreach(const QFileInfo & drive, QDir::drives()) {
|
||||
temppath = drive.absolutePath();
|
||||
if (blacklist.contains(temppath))
|
||||
continue;
|
||||
if (!isRemovableMedia(temppath)) {
|
||||
blacklist.append(temppath);
|
||||
continue;
|
||||
}
|
||||
WCHAR szVolumeName[256] ;
|
||||
WCHAR szFileSystemName[256];
|
||||
DWORD dwSerialNumber = 0;
|
||||
DWORD dwMaxFileNameLength=256;
|
||||
DWORD dwFileSystemFlags=0;
|
||||
if (!blacklist.contains(drive.absolutePath())) {
|
||||
if (!isRemovableMedia( drive.absolutePath() )) {
|
||||
blacklist.append(drive.absolutePath());
|
||||
} else {
|
||||
bool ret = GetVolumeInformationW( (WCHAR *) drive.absolutePath().utf16(),szVolumeName,256,&dwSerialNumber,&dwMaxFileNameLength,&dwFileSystemFlags,szFileSystemName,256);
|
||||
if (ret) {
|
||||
QString vName = QString::fromUtf16 ( (const ushort *) szVolumeName) ;
|
||||
temppath = drive.absolutePath();
|
||||
eepromfile = temppath;
|
||||
eepromfile.append("/" + filename);
|
||||
if (QFile::exists(eepromfile)) {
|
||||
return onlyPath ? temppath : eepromfile;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (!GetVolumeInformationW( (WCHAR *) drive.absolutePath().utf16(),szVolumeName,256,&dwSerialNumber,&dwMaxFileNameLength,&dwFileSystemFlags,szFileSystemName,256))
|
||||
continue;
|
||||
eepromfile = temppath % "/" % filename;
|
||||
qDebug() << "Searching for" << eepromfile;
|
||||
if (QFile::exists(eepromfile)) {
|
||||
found = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
#else
|
||||
const static QStringList blacklist = QStringList() << "/" << "/net" << "/proc" << "/run";
|
||||
QStringList drives;
|
||||
struct mount_entry *entry;
|
||||
struct mount_entry *firstEntry;
|
||||
firstEntry = entry = read_file_system_list(true);
|
||||
while (entry != NULL) {
|
||||
if (!drives.contains(entry->me_devname)) {
|
||||
temppath = entry->me_mountdir;
|
||||
if (!drives.contains(entry->me_devname) && !blacklist.contains(temppath) && QString(entry->me_type).contains(fstypeRe)) {
|
||||
drives.append(entry->me_devname);
|
||||
temppath = entry->me_mountdir;
|
||||
eepromfile = temppath;
|
||||
eepromfile.append("/" + filename);
|
||||
eepromfile = temppath % "/" % filename;
|
||||
qDebug() << "Searching for" << eepromfile;
|
||||
#if !defined __APPLE__
|
||||
QString fstype = entry->me_type;
|
||||
// qDebug() << eepromfile;
|
||||
|
||||
if (fstype.contains("fat") && QFile::exists(eepromfile)) {
|
||||
#else
|
||||
if (QFile::exists(eepromfile)) {
|
||||
#endif
|
||||
free_file_system_list(firstEntry);
|
||||
return onlyPath ? temppath : eepromfile;
|
||||
found = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
entry = entry->me_next;
|
||||
@@ -477,5 +482,8 @@ QString findMassstoragePath(const QString & filename, bool onlyPath)
|
||||
free_file_system_list(firstEntry);
|
||||
#endif
|
||||
|
||||
return QString();
|
||||
if (found)
|
||||
return onlyPath ? temppath : eepromfile;
|
||||
else
|
||||
return QString();
|
||||
}
|
||||
|
||||
@@ -267,7 +267,7 @@ QWidget * RadioOutputsWidget::createLogicalSwitch(QWidget * parent, int switchNo
|
||||
swtch->setMinimumWidth(swtch->fontMetrics().width("99") + 10);
|
||||
font.setBold(false);
|
||||
swtch->setFont(font);
|
||||
swtch->setText(QString("%1").arg(RawSwitch(SWITCH_TYPE_VIRTUAL, switchNo+1).toString().remove("L"), 2, QLatin1Char('0')));
|
||||
swtch->setText(QString("%1").arg(switchNo+1, 2, 10, QChar('0')));
|
||||
swtch->setAlignment(Qt::AlignCenter);
|
||||
m_logicSwitchMap.insert(switchNo, swtch);
|
||||
return swtch;
|
||||
|
||||
@@ -38,40 +38,40 @@ SimulatedUIWidget9X::SimulatedUIWidget9X(SimulatorInterface * simulator, QWidget
|
||||
int x = 68, y = 91, oR = 63;
|
||||
|
||||
polygon << QPoint(x, y) << polyArc(x, y, oR, -45, 45);
|
||||
act = new RadioUiAction(3, QList<int>() << Qt::Key_Up << Qt::Key_PageUp, tr(SIMU_STR_HLP_KEYS_GO_UP) % (hasRotEnc ? "" : tr("|" SIMU_STR_HLP_MOUSE_UP)), tr(SIMU_STR_HLP_ACT_UP));
|
||||
act = new RadioUiAction(3, QList<int>() << Qt::Key_Up << Qt::Key_PageUp, SIMU_STR_HLP_KEYS_GO_UP % (hasRotEnc ? QString("") : "|" % SIMU_STR_HLP_MOUSE_UP), SIMU_STR_HLP_ACT_UP);
|
||||
addRadioWidget(ui->leftbuttons->addArea(polygon, "9X/9xcursup.png", act));
|
||||
|
||||
polygon.clear();
|
||||
polygon << QPoint(x, y) << polyArc(x, y, oR, 135, 225);
|
||||
act = new RadioUiAction(2, QList<int>() << Qt::Key_Down << Qt::Key_PageDown, tr(SIMU_STR_HLP_KEYS_GO_DN) % (hasRotEnc ? "" : tr("|" SIMU_STR_HLP_MOUSE_DN)), tr(SIMU_STR_HLP_ACT_DN));
|
||||
act = new RadioUiAction(2, QList<int>() << Qt::Key_Down << Qt::Key_PageDown, SIMU_STR_HLP_KEYS_GO_DN % (hasRotEnc ? QString("") : "|" % SIMU_STR_HLP_MOUSE_DN), SIMU_STR_HLP_ACT_DN);
|
||||
addRadioWidget(ui->leftbuttons->addArea(polygon, "9X/9xcursdown.png", act));
|
||||
|
||||
polygon.clear();
|
||||
polygon << QPoint(x, y) << polyArc(x, y, oR, 45, 135);
|
||||
act = new RadioUiAction(4, QList<int>() << Qt::Key_Right << Qt::Key_Minus, tr(SIMU_STR_HLP_KEY_RGT "|" SIMU_STR_HLP_KEY_MIN), tr(SIMU_STR_HLP_ACT_MIN));
|
||||
act = new RadioUiAction(4, QList<int>() << Qt::Key_Right << Qt::Key_Minus, SIMU_STR_HLP_KEY_RGT % "|" % SIMU_STR_HLP_KEY_MIN, SIMU_STR_HLP_ACT_MIN);
|
||||
addRadioWidget(ui->leftbuttons->addArea(polygon, "9X/9xcursmin.png", act));
|
||||
|
||||
polygon.clear();
|
||||
polygon << QPoint(x, y) << polyArc(x, y, oR, 225, 315);
|
||||
act = new RadioUiAction(5, QList<int>() << Qt::Key_Left << Qt::Key_Plus << Qt::Key_Equal, tr(SIMU_STR_HLP_KEY_LFT "|" SIMU_STR_HLP_KEY_PLS), tr(SIMU_STR_HLP_ACT_PLS));
|
||||
act = new RadioUiAction(5, QList<int>() << Qt::Key_Left << Qt::Key_Plus << Qt::Key_Equal, SIMU_STR_HLP_KEY_LFT % "|" % SIMU_STR_HLP_KEY_PLS, SIMU_STR_HLP_ACT_PLS);
|
||||
addRadioWidget(ui->leftbuttons->addArea(polygon, "9X/9xcursplus.png", act));
|
||||
|
||||
act = new RadioUiAction(0, QList<int>() << Qt::Key_Enter << Qt::Key_Return, tr(SIMU_STR_HLP_KEY_ENTER), tr(SIMU_STR_HLP_ACT_MENU));
|
||||
act = new RadioUiAction(0, QList<int>() << Qt::Key_Enter << Qt::Key_Return, SIMU_STR_HLP_KEY_ENTER, SIMU_STR_HLP_ACT_MENU);
|
||||
addRadioWidget(ui->rightbuttons->addArea(QRect(16, 54, 60, 34), "9X/9xmenumenu.png", act));
|
||||
|
||||
if (!hasRotEnc) {
|
||||
m_mouseMidClickAction = act;
|
||||
m_mouseMidClickAction->setText(act->getText() % "|" SIMU_STR_HLP_MOUSE_MID);
|
||||
m_mouseMidClickAction->setText(act->getText() % "|" % SIMU_STR_HLP_MOUSE_MID);
|
||||
}
|
||||
|
||||
act = new RadioUiAction(1, QList<int>() << Qt::Key_Delete << Qt::Key_Escape << Qt::Key_Backspace, tr(SIMU_STR_HLP_KEYS_EXIT), tr(SIMU_STR_HLP_ACT_EXIT));
|
||||
act = new RadioUiAction(1, QList<int>() << Qt::Key_Delete << Qt::Key_Escape << Qt::Key_Backspace, SIMU_STR_HLP_KEYS_EXIT, SIMU_STR_HLP_ACT_EXIT);
|
||||
addRadioWidget(ui->rightbuttons->addArea(QRect(16, 114, 60, 34), "9X/9xmenuexit.png", act));
|
||||
|
||||
addRadioWidget(ui->leftbuttons->addArea(QRect(6, 149, 30, 30), "9X/9xcursphoto.png", m_screenshotAction));
|
||||
|
||||
if (hasRotEnc) {
|
||||
addRadioAction(new RadioUiAction(-1, 0, tr(SIMU_STR_HLP_MOUSE_SCRL), tr(SIMU_STR_HLP_ROTENC " " SIMU_STR_HLP_ROTENC_LR)));
|
||||
m_mouseMidClickAction = new RadioUiAction(14, Qt::Key_Insert, tr(SIMU_STR_HLP_KEY_INS "|" SIMU_STR_HLP_MOUSE_MID), tr(SIMU_STR_HLP_ACT_ROT_DN));
|
||||
addRadioAction(new RadioUiAction(-1, 0, SIMU_STR_HLP_MOUSE_SCRL, SIMU_STR_HLP_ROTENC % "|" % SIMU_STR_HLP_ROTENC_LR));
|
||||
m_mouseMidClickAction = new RadioUiAction(14, Qt::Key_Insert, SIMU_STR_HLP_KEY_INS % "|" % SIMU_STR_HLP_MOUSE_MID, SIMU_STR_HLP_ACT_ROT_DN);
|
||||
addRadioWidget(ui->leftbuttons->addArea(QRect(0, 0, 0, 0), "9X/9xcurs.png", m_mouseMidClickAction));
|
||||
}
|
||||
|
||||
|
||||
@@ -35,40 +35,40 @@ SimulatedUIWidgetX12::SimulatedUIWidgetX12(SimulatorInterface *simulator, QWidge
|
||||
int x = 74, y = 190, oR = 63, iR = 40;
|
||||
|
||||
polygon << polyArc(x, y, oR, 225, 315) << polyArc(x, y, iR, 225, 315);
|
||||
act = new RadioUiAction(0, QList<int>() << Qt::Key_PageUp, tr(SIMU_STR_HLP_KEY_PGUP), tr(SIMU_STR_HLP_ACT_PGUP));
|
||||
act = new RadioUiAction(0, QList<int>() << Qt::Key_PageUp, SIMU_STR_HLP_KEY_PGUP, SIMU_STR_HLP_ACT_PGUP);
|
||||
addRadioWidget(ui->leftbuttons->addArea(polygon, "Horus/left_btn1.png", act));
|
||||
|
||||
polygon.clear();
|
||||
polygon << polyArc(x, y, oR, 135, 225) << polyArc(x, y, iR, 135, 225);
|
||||
act = new RadioUiAction(1, QList<int>() << Qt::Key_PageDown, tr(SIMU_STR_HLP_KEY_PGDN), tr(SIMU_STR_HLP_ACT_PGDN));
|
||||
act = new RadioUiAction(1, QList<int>() << Qt::Key_PageDown, SIMU_STR_HLP_KEY_PGDN, SIMU_STR_HLP_ACT_PGDN);
|
||||
addRadioWidget(ui->leftbuttons->addArea(polygon, "Horus/left_btn2.png", act));
|
||||
|
||||
polygon.clear();
|
||||
polygon << polyArc(x, y, oR, -45, 45) << polyArc(x, y, iR, -45, 45);
|
||||
act = new RadioUiAction(3, QList<int>() << Qt::Key_Up, tr(SIMU_STR_HLP_KEY_UP), tr(SIMU_STR_HLP_ACT_MDL));
|
||||
act = new RadioUiAction(3, QList<int>() << Qt::Key_Up, SIMU_STR_HLP_KEY_UP, SIMU_STR_HLP_ACT_MDL);
|
||||
addRadioWidget(ui->rightbuttons->addArea(polygon, "Horus/right_btnU.png", act));
|
||||
|
||||
polygon.clear();
|
||||
polygon << polyArc(x, y, oR, 225, 315) << polyArc(x, y, iR, 225, 315);
|
||||
act = new RadioUiAction(6, QList<int>() << Qt::Key_Left, tr(SIMU_STR_HLP_KEY_LFT), tr(SIMU_STR_HLP_ACT_SYS));
|
||||
act = new RadioUiAction(6, QList<int>() << Qt::Key_Left, SIMU_STR_HLP_KEY_LFT, SIMU_STR_HLP_ACT_SYS);
|
||||
addRadioWidget(ui->rightbuttons->addArea(polygon, "Horus/right_btnL.png", act));
|
||||
|
||||
polygon.clear();
|
||||
polygon << polyArc(x, y, oR, 45, 135) << polyArc(x, y, iR, 45, 135);
|
||||
act = new RadioUiAction(5, QList<int>() << Qt::Key_Right, tr(SIMU_STR_HLP_KEY_RGT), tr(SIMU_STR_HLP_ACT_TELE));
|
||||
act = new RadioUiAction(5, QList<int>() << Qt::Key_Right, SIMU_STR_HLP_KEY_RGT, SIMU_STR_HLP_ACT_TELE);
|
||||
addRadioWidget(ui->rightbuttons->addArea(polygon, "Horus/right_btnR.png", act));
|
||||
|
||||
polygon.clear();
|
||||
polygon << polyArc(x, y, oR, 135, 225) << polyArc(x, y, iR, 135, 225);
|
||||
act = new RadioUiAction(4, QList<int>() << Qt::Key_Down << Qt::Key_Delete << Qt::Key_Escape << Qt::Key_Backspace,
|
||||
tr(SIMU_STR_HLP_KEY_DN "<br>" SIMU_STR_HLP_KEYS_EXIT), tr(SIMU_STR_HLP_ACT_RTN));
|
||||
SIMU_STR_HLP_KEY_DN % "<br>" % SIMU_STR_HLP_KEYS_EXIT, SIMU_STR_HLP_ACT_RTN);
|
||||
addRadioWidget(ui->rightbuttons->addArea(polygon, "Horus/right_btnD.png", act));
|
||||
|
||||
m_scrollUpAction = new RadioUiAction(-1, QList<int>() << Qt::Key_Minus, tr(SIMU_STR_HLP_KEY_MIN "|" SIMU_STR_HLP_MOUSE_UP), tr(SIMU_STR_HLP_ACT_ROT_LFT));
|
||||
m_scrollDnAction = new RadioUiAction(-1, QList<int>() << Qt::Key_Plus << Qt::Key_Equal, tr(SIMU_STR_HLP_KEY_PLS "|" SIMU_STR_HLP_MOUSE_DN), tr(SIMU_STR_HLP_ACT_ROT_RGT));
|
||||
m_scrollUpAction = new RadioUiAction(-1, QList<int>() << 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<int>() << 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<int>() << Qt::Key_Enter << Qt::Key_Return, tr(SIMU_STR_HLP_KEYS_ACTIVATE), tr(SIMU_STR_HLP_ACT_ROT_DN));
|
||||
m_mouseMidClickAction = new RadioUiAction(2, QList<int>() << 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->leftbuttons->addArea(QRect(9, 259, 30, 30), "Horus/left_scrnsht.png", m_screenshotAction));
|
||||
|
||||
@@ -14,22 +14,22 @@ SimulatedUIWidgetX7::SimulatedUIWidgetX7(SimulatorInterface *simulator, QWidget
|
||||
|
||||
QPoint ctr(70, 91);
|
||||
polygon << polyArc(ctr.x(), ctr.y(), 50, -90, 90) << polyArc(ctr.x(), ctr.y(), 22, -90, 90);
|
||||
act = new RadioUiAction(3, QList<int>() << Qt::Key_PageUp << Qt::Key_Up, tr(SIMU_STR_HLP_KEYS_GO_UP), tr(SIMU_STR_HLP_ACT_PAGE));
|
||||
act = new RadioUiAction(3, QList<int>() << Qt::Key_PageUp << Qt::Key_Up, SIMU_STR_HLP_KEYS_GO_UP, SIMU_STR_HLP_ACT_PAGE);
|
||||
addRadioWidget(ui->leftbuttons->addArea(polygon, "X7/left_page.png", act));
|
||||
|
||||
act = new RadioUiAction(0, QList<int>() << Qt::Key_PageDown << Qt::Key_Down, tr(SIMU_STR_HLP_KEYS_GO_DN), tr(SIMU_STR_HLP_ACT_MENU_ICN));
|
||||
act = new RadioUiAction(0, QList<int>() << Qt::Key_PageDown << Qt::Key_Down, SIMU_STR_HLP_KEYS_GO_DN, SIMU_STR_HLP_ACT_MENU_ICN);
|
||||
addRadioWidget(ui->leftbuttons->addArea(polyArc(ctr.x(), ctr.y(), 20), "X7/left_menu.png", act));
|
||||
|
||||
polygon.clear();
|
||||
polygon << polyArc(ctr.x(), ctr.y(), 50, 90, 270) << polyArc(ctr.x(), ctr.y(), 22, 90, 270);
|
||||
act = new RadioUiAction(1, QList<int>() << Qt::Key_Delete << Qt::Key_Escape << Qt::Key_Backspace, tr(SIMU_STR_HLP_KEYS_EXIT), tr(SIMU_STR_HLP_ACT_EXIT));
|
||||
act = new RadioUiAction(1, QList<int>() << Qt::Key_Delete << Qt::Key_Escape << Qt::Key_Backspace, SIMU_STR_HLP_KEYS_EXIT, SIMU_STR_HLP_ACT_EXIT);
|
||||
addRadioWidget(ui->leftbuttons->addArea(polygon, "X7/left_exit.png", act));
|
||||
|
||||
m_scrollUpAction = new RadioUiAction(-1, QList<int>() << Qt::Key_Minus << Qt::Key_Equal << Qt::Key_Left, tr(SIMU_STR_HLP_KEYS_GO_LFT), tr(SIMU_STR_HLP_ACT_ROT_LFT));
|
||||
m_scrollDnAction = new RadioUiAction(-1, QList<int>() << Qt::Key_Plus << Qt::Key_Right, tr(SIMU_STR_HLP_KEYS_GO_RGT), tr(SIMU_STR_HLP_ACT_ROT_RGT));
|
||||
m_scrollUpAction = new RadioUiAction(-1, QList<int>() << Qt::Key_Minus << Qt::Key_Equal << Qt::Key_Left, SIMU_STR_HLP_KEYS_GO_LFT, SIMU_STR_HLP_ACT_ROT_LFT);
|
||||
m_scrollDnAction = new RadioUiAction(-1, QList<int>() << Qt::Key_Plus << Qt::Key_Right, SIMU_STR_HLP_KEYS_GO_RGT, SIMU_STR_HLP_ACT_ROT_RGT);
|
||||
connectScrollActions();
|
||||
|
||||
m_mouseMidClickAction = new RadioUiAction(2, QList<int>() << Qt::Key_Enter << Qt::Key_Return, tr(SIMU_STR_HLP_KEYS_ACTIVATE), tr(SIMU_STR_HLP_ACT_ROT_DN));
|
||||
m_mouseMidClickAction = new RadioUiAction(2, QList<int>() << Qt::Key_Enter << Qt::Key_Return, SIMU_STR_HLP_KEYS_ACTIVATE, SIMU_STR_HLP_ACT_ROT_DN);
|
||||
addRadioWidget(ui->rightbuttons->addArea(polyArc(88, 92, 33), "X7/right_ent.png", m_mouseMidClickAction));
|
||||
|
||||
addRadioWidget(ui->leftbuttons->addArea(QRect(9, 154, 30, 30), "X7/left_scrnshot.png", m_screenshotAction));
|
||||
|
||||
@@ -37,21 +37,21 @@ SimulatedUIWidgetX9::SimulatedUIWidgetX9(SimulatorInterface *simulator, QWidget
|
||||
|
||||
// left side
|
||||
|
||||
act = new RadioUiAction(0, QList<int>() << Qt::Key_Up << Qt::Key_PageUp, tr(SIMU_STR_HLP_KEYS_GO_UP), tr(SIMU_STR_HLP_ACT_MENU));
|
||||
act = new RadioUiAction(0, QList<int>() << Qt::Key_Up << Qt::Key_PageUp, SIMU_STR_HLP_KEYS_GO_UP, SIMU_STR_HLP_ACT_MENU);
|
||||
addRadioWidget(ui->leftbuttons->addArea(btn, "Taranis/x9l1.png", act));
|
||||
btn.moveTop(btn.top() + btn.height() + vsp);
|
||||
|
||||
act = new RadioUiAction(3, QList<int>() << Qt::Key_Down << Qt::Key_PageDown, tr(SIMU_STR_HLP_KEYS_GO_DN), tr(SIMU_STR_HLP_ACT_PAGE));
|
||||
act = new RadioUiAction(3, QList<int>() << Qt::Key_Down << Qt::Key_PageDown, SIMU_STR_HLP_KEYS_GO_DN, SIMU_STR_HLP_ACT_PAGE);
|
||||
addRadioWidget(ui->leftbuttons->addArea(btn, "Taranis/x9l2.png", act));
|
||||
btn.moveTop(btn.top() + btn.height() + vsp);
|
||||
|
||||
act = new RadioUiAction(1, QList<int>() << Qt::Key_Delete << Qt::Key_Escape << Qt::Key_Backspace, tr(SIMU_STR_HLP_KEYS_EXIT), tr(SIMU_STR_HLP_ACT_EXIT));
|
||||
act = new RadioUiAction(1, QList<int>() << Qt::Key_Delete << Qt::Key_Escape << Qt::Key_Backspace, SIMU_STR_HLP_KEYS_EXIT, SIMU_STR_HLP_ACT_EXIT);
|
||||
addRadioWidget(ui->leftbuttons->addArea(btn, "Taranis/x9l3.png", act));
|
||||
|
||||
m_scrollUpAction = new RadioUiAction(4, QList<int>() << Qt::Key_Plus << Qt::Key_Equal << Qt::Key_Left,
|
||||
tr(SIMU_STR_HLP_KEY_LFT "|" SIMU_STR_HLP_KEY_PLS "|" SIMU_STR_HLP_MOUSE_UP), tr(SIMU_STR_HLP_ACT_PLS));
|
||||
SIMU_STR_HLP_KEY_LFT % "|" % SIMU_STR_HLP_KEY_PLS % "|" % SIMU_STR_HLP_MOUSE_UP, SIMU_STR_HLP_ACT_PLS);
|
||||
m_scrollDnAction = new RadioUiAction(5, QList<int>() << Qt::Key_Minus << Qt::Key_Right,
|
||||
tr(SIMU_STR_HLP_KEY_RGT "|" SIMU_STR_HLP_KEY_MIN "|" SIMU_STR_HLP_MOUSE_DN), tr(SIMU_STR_HLP_ACT_MIN));
|
||||
SIMU_STR_HLP_KEY_RGT % "|" % SIMU_STR_HLP_KEY_MIN % "|" % SIMU_STR_HLP_MOUSE_DN, SIMU_STR_HLP_ACT_MIN);
|
||||
|
||||
// right side
|
||||
btn.moveTopLeft(QPoint(58, btop));
|
||||
@@ -62,7 +62,7 @@ SimulatedUIWidgetX9::SimulatedUIWidgetX9(SimulatorInterface *simulator, QWidget
|
||||
addRadioWidget(ui->rightbuttons->addArea(btn, "Taranis/x9r2.png", m_scrollDnAction));
|
||||
btn.moveTop(btn.top() + btn.height() + vsp);
|
||||
|
||||
m_mouseMidClickAction = new RadioUiAction(2, QList<int>() << Qt::Key_Enter << Qt::Key_Return, tr(SIMU_STR_HLP_KEYS_ACTIVATE), tr(SIMU_STR_HLP_ACT_ENT));
|
||||
m_mouseMidClickAction = new RadioUiAction(2, QList<int>() << Qt::Key_Enter << Qt::Key_Return, SIMU_STR_HLP_KEYS_ACTIVATE, SIMU_STR_HLP_ACT_ENT);
|
||||
addRadioWidget(ui->rightbuttons->addArea(btn, "Taranis/x9r3.png", m_mouseMidClickAction));
|
||||
|
||||
addRadioWidget(ui->leftbuttons->addArea(QRect(89, 177, 30, 20), "Taranis/x9l4.png", m_screenshotAction));
|
||||
|
||||
@@ -35,24 +35,24 @@ SimulatedUIWidgetX9E::SimulatedUIWidgetX9E(SimulatorInterface *simulator, QWidge
|
||||
QPoint ctr(70, 100);
|
||||
|
||||
polygon << polyArc(ctr.x(), ctr.y(), 60, -90, 0) << ctr;
|
||||
act = new RadioUiAction(0, QList<int>() << Qt::Key_Up << Qt::Key_PageUp, tr(SIMU_STR_HLP_KEYS_GO_UP), tr(SIMU_STR_HLP_ACT_MENU));
|
||||
act = new RadioUiAction(0, QList<int>() << Qt::Key_Up << Qt::Key_PageUp, SIMU_STR_HLP_KEYS_GO_UP, SIMU_STR_HLP_ACT_MENU);
|
||||
addRadioWidget(ui->leftbuttons->addArea(polygon, "X9E/left_menu.png", act));
|
||||
|
||||
polygon.clear();
|
||||
polygon << polyArc(ctr.x(), ctr.y(), 45, 0, 180);
|
||||
act = new RadioUiAction(3, QList<int>() << Qt::Key_Down << Qt::Key_PageDown, tr(SIMU_STR_HLP_KEYS_GO_DN), tr(SIMU_STR_HLP_ACT_PAGE));
|
||||
act = new RadioUiAction(3, QList<int>() << Qt::Key_Down << Qt::Key_PageDown, SIMU_STR_HLP_KEYS_GO_DN, SIMU_STR_HLP_ACT_PAGE);
|
||||
addRadioWidget(ui->leftbuttons->addArea(polygon, "X9E/left_page.png", act));
|
||||
|
||||
polygon.clear();
|
||||
polygon << polyArc(ctr.x(), ctr.y(), 60, 180, 270) << ctr;
|
||||
act = new RadioUiAction(1, QList<int>() << Qt::Key_Delete << Qt::Key_Escape << Qt::Key_Backspace, tr(SIMU_STR_HLP_KEYS_EXIT), tr(SIMU_STR_HLP_ACT_EXIT));
|
||||
act = new RadioUiAction(1, QList<int>() << Qt::Key_Delete << Qt::Key_Escape << Qt::Key_Backspace, SIMU_STR_HLP_KEYS_EXIT, SIMU_STR_HLP_ACT_EXIT);
|
||||
addRadioWidget(ui->leftbuttons->addArea(polygon, "X9E/left_exit.png", act));
|
||||
|
||||
m_scrollUpAction = addRadioAction(new RadioUiAction(-1, QList<int>() << Qt::Key_Minus << Qt::Key_Left, tr(SIMU_STR_HLP_KEYS_GO_LFT), tr(SIMU_STR_HLP_ACT_ROT_LFT)));
|
||||
m_scrollDnAction = addRadioAction(new RadioUiAction(-1, QList<int>() << Qt::Key_Plus << Qt::Key_Equal << Qt::Key_Right, tr(SIMU_STR_HLP_KEYS_GO_RGT), tr(SIMU_STR_HLP_ACT_ROT_RGT)));
|
||||
m_scrollUpAction = addRadioAction(new RadioUiAction(-1, QList<int>() << Qt::Key_Minus << Qt::Key_Left, SIMU_STR_HLP_KEYS_GO_LFT, SIMU_STR_HLP_ACT_ROT_LFT));
|
||||
m_scrollDnAction = addRadioAction(new RadioUiAction(-1, QList<int>() << Qt::Key_Plus << Qt::Key_Equal << Qt::Key_Right, SIMU_STR_HLP_KEYS_GO_RGT, SIMU_STR_HLP_ACT_ROT_RGT));
|
||||
connectScrollActions();
|
||||
|
||||
m_mouseMidClickAction = new RadioUiAction(2, QList<int>() << Qt::Key_Enter << Qt::Key_Return, tr(SIMU_STR_HLP_KEYS_ACTIVATE), tr(SIMU_STR_HLP_ACT_ROT_DN));
|
||||
m_mouseMidClickAction = new RadioUiAction(2, QList<int>() << Qt::Key_Enter << Qt::Key_Return, SIMU_STR_HLP_KEYS_ACTIVATE, SIMU_STR_HLP_ACT_ROT_DN);
|
||||
addRadioWidget(ui->rightbuttons->addArea(polyArc(90, 100, 50), "X9E/right_enter.png", m_mouseMidClickAction));
|
||||
|
||||
addRadioWidget(ui->leftbuttons->addArea(QRect(10, 170, 30, 30), "X9E/left_scrnshot.png", m_screenshotAction));
|
||||
|
||||
@@ -1,66 +1,66 @@
|
||||
#ifndef SIMULATOR_STRINGS_H
|
||||
#define SIMULATOR_STRINGS_H
|
||||
|
||||
#include <QtGlobal>
|
||||
#include <QCoreApplication>
|
||||
|
||||
#define SIMU_STR_HLP_KEY_ENTER QT_TRANSLATE_NOOP("SimulatedUIWidget", "ENTER")
|
||||
#define SIMU_STR_HLP_KEY_PGUP QT_TRANSLATE_NOOP("SimulatedUIWidget", "PG-UP")
|
||||
#define SIMU_STR_HLP_KEY_PGDN QT_TRANSLATE_NOOP("SimulatedUIWidget", "PG-DN")
|
||||
#define SIMU_STR_HLP_KEY_DEL QT_TRANSLATE_NOOP("SimulatedUIWidget", "DEL")
|
||||
#define SIMU_STR_HLP_KEY_BKSP QT_TRANSLATE_NOOP("SimulatedUIWidget", "BKSP")
|
||||
#define SIMU_STR_HLP_KEY_ESC QT_TRANSLATE_NOOP("SimulatedUIWidget", "ESC")
|
||||
#define SIMU_STR_HLP_KEY_INS QT_TRANSLATE_NOOP("SimulatedUIWidget", "INS")
|
||||
#define SIMU_STR_HLP_KEY_PLS QT_TRANSLATE_NOOP("SimulatedUIWidget", "<font size=+3>+</font>")
|
||||
#define SIMU_STR_HLP_KEY_MIN QT_TRANSLATE_NOOP("SimulatedUIWidget", "<font size=+3>-</font>")
|
||||
#define SIMU_STR_HLP_KEY_ENTER QCoreApplication::translate("SimulatedUIWidget", "ENTER")
|
||||
#define SIMU_STR_HLP_KEY_PGUP QCoreApplication::translate("SimulatedUIWidget", "PG-UP")
|
||||
#define SIMU_STR_HLP_KEY_PGDN QCoreApplication::translate("SimulatedUIWidget", "PG-DN")
|
||||
#define SIMU_STR_HLP_KEY_DEL QCoreApplication::translate("SimulatedUIWidget", "DEL")
|
||||
#define SIMU_STR_HLP_KEY_BKSP QCoreApplication::translate("SimulatedUIWidget", "BKSP")
|
||||
#define SIMU_STR_HLP_KEY_ESC QCoreApplication::translate("SimulatedUIWidget", "ESC")
|
||||
#define SIMU_STR_HLP_KEY_INS QCoreApplication::translate("SimulatedUIWidget", "INS")
|
||||
#define SIMU_STR_HLP_KEY_PLS QCoreApplication::translate("SimulatedUIWidget", "<font size=+3>+</font>")
|
||||
#define SIMU_STR_HLP_KEY_MIN QCoreApplication::translate("SimulatedUIWidget", "<font size=+3>-</font>")
|
||||
|
||||
#define SIMU_STR_HLP_KEY_LFT QT_TRANSLATE_NOOP("SimulatedUIWidget", "<font size=+3>←</font>") // ←
|
||||
#define SIMU_STR_HLP_KEY_RGT QT_TRANSLATE_NOOP("SimulatedUIWidget", "<font size=+3>→</font>") // →
|
||||
#define SIMU_STR_HLP_KEY_UP QT_TRANSLATE_NOOP("SimulatedUIWidget", "<font size=+3>↑</font>") // ↑
|
||||
#define SIMU_STR_HLP_KEY_DN QT_TRANSLATE_NOOP("SimulatedUIWidget", "<font size=+3>↓</font>") // ↓
|
||||
#define SIMU_STR_HLP_KEY_LFT QCoreApplication::translate("SimulatedUIWidget", "<font size=+3>←</font>") // ←
|
||||
#define SIMU_STR_HLP_KEY_RGT QCoreApplication::translate("SimulatedUIWidget", "<font size=+3>→</font>") // →
|
||||
#define SIMU_STR_HLP_KEY_UP QCoreApplication::translate("SimulatedUIWidget", "<font size=+3>↑</font>") // ↑
|
||||
#define SIMU_STR_HLP_KEY_DN QCoreApplication::translate("SimulatedUIWidget", "<font size=+3>↓</font>") // ↓
|
||||
|
||||
#define SIMU_STR_HLP_ROTENC QT_TRANSLATE_NOOP("SimulatedUIWidget", "<font size=+3>⚆</font>") // ⚆
|
||||
#define SIMU_STR_HLP_ROTENC_LFT QT_TRANSLATE_NOOP("SimulatedUIWidget", "<font size=+3>↶</font>") // ↶
|
||||
#define SIMU_STR_HLP_ROTENC_RGT QT_TRANSLATE_NOOP("SimulatedUIWidget", "<font size=+3>↷</font>") // ↷
|
||||
#define SIMU_STR_HLP_ROTENC_LR QT_TRANSLATE_NOOP("SimulatedUIWidget", "<font size=+3>⇆</font>") // ⇆
|
||||
#define SIMU_STR_HLP_ROTENC_DN QT_TRANSLATE_NOOP("SimulatedUIWidget", "<font size=+3>⇓</font>") // ⇓
|
||||
#define SIMU_STR_HLP_ROTENC QCoreApplication::translate("SimulatedUIWidget", "<font size=+3>⚆</font>") // ⚆
|
||||
#define SIMU_STR_HLP_ROTENC_LFT QCoreApplication::translate("SimulatedUIWidget", "<font size=+3>↶</font>") // ↶
|
||||
#define SIMU_STR_HLP_ROTENC_RGT QCoreApplication::translate("SimulatedUIWidget", "<font size=+3>↷</font>") // ↷
|
||||
#define SIMU_STR_HLP_ROTENC_LR QCoreApplication::translate("SimulatedUIWidget", "<font size=+3>⇆</font>") // ⇆
|
||||
#define SIMU_STR_HLP_ROTENC_DN QCoreApplication::translate("SimulatedUIWidget", "<font size=+3>⇓</font>") // ⇓
|
||||
|
||||
#define SIMU_STR_HLP_SCRL_UP QT_TRANSLATE_NOOP("SimulatedUIWidget", "<font size=+3>⇑</font>") // ⇑
|
||||
#define SIMU_STR_HLP_SCRL_DN QT_TRANSLATE_NOOP("SimulatedUIWidget", "<font size=+3>⇓</font>") // ⇓
|
||||
#define SIMU_STR_HLP_SCRL_UD QT_TRANSLATE_NOOP("SimulatedUIWidget", "<font size=+3>⇕</font>") // ⇕
|
||||
#define SIMU_STR_HLP_SCRL_UP QCoreApplication::translate("SimulatedUIWidget", "<font size=+3>⇑</font>") // ⇑
|
||||
#define SIMU_STR_HLP_SCRL_DN QCoreApplication::translate("SimulatedUIWidget", "<font size=+3>⇓</font>") // ⇓
|
||||
#define SIMU_STR_HLP_SCRL_UD QCoreApplication::translate("SimulatedUIWidget", "<font size=+3>⇕</font>") // ⇕
|
||||
|
||||
#define SIMU_STR_HLP_MOUSE QT_TRANSLATE_NOOP("SimulatedUIWidget", "<img src='qrc:/images/simulator/icons/svg/mouse.svg' width=20 height=18 />")
|
||||
#define SIMU_STR_HLP_CLICK QT_TRANSLATE_NOOP("SimulatedUIWidget", "<img src='qrc:/images/simulator/icons/svg/arrow_click.svg' width=18 height=18 />")
|
||||
#define SIMU_STR_HLP_MOUSE_MID SIMU_STR_HLP_MOUSE SIMU_STR_HLP_CLICK
|
||||
#define SIMU_STR_HLP_MOUSE_UP SIMU_STR_HLP_MOUSE SIMU_STR_HLP_SCRL_UP
|
||||
#define SIMU_STR_HLP_MOUSE_DN SIMU_STR_HLP_MOUSE SIMU_STR_HLP_SCRL_DN
|
||||
#define SIMU_STR_HLP_MOUSE_SCRL SIMU_STR_HLP_MOUSE SIMU_STR_HLP_SCRL_UD
|
||||
#define SIMU_STR_HLP_MOUSE QCoreApplication::translate("SimulatedUIWidget", "<img src='qrc:/images/simulator/icons/svg/mouse.svg' width=20 height=18 />")
|
||||
#define SIMU_STR_HLP_CLICK QCoreApplication::translate("SimulatedUIWidget", "<img src='qrc:/images/simulator/icons/svg/arrow_click.svg' width=18 height=18 />")
|
||||
#define SIMU_STR_HLP_MOUSE_MID SIMU_STR_HLP_MOUSE % SIMU_STR_HLP_CLICK
|
||||
#define SIMU_STR_HLP_MOUSE_UP SIMU_STR_HLP_MOUSE % SIMU_STR_HLP_SCRL_UP
|
||||
#define SIMU_STR_HLP_MOUSE_DN SIMU_STR_HLP_MOUSE % SIMU_STR_HLP_SCRL_DN
|
||||
#define SIMU_STR_HLP_MOUSE_SCRL SIMU_STR_HLP_MOUSE % SIMU_STR_HLP_SCRL_UD
|
||||
|
||||
#define SIMU_STR_HLP_ACT_MENU QT_TRANSLATE_NOOP("SimulatedUIWidget", "<pre>[ MENU ]</pre>")
|
||||
#define SIMU_STR_HLP_ACT_PAGE QT_TRANSLATE_NOOP("SimulatedUIWidget", "<pre>[ PAGE ]</pre>")
|
||||
#define SIMU_STR_HLP_ACT_EXIT QT_TRANSLATE_NOOP("SimulatedUIWidget", "<pre>[ EXIT ]</pre>")
|
||||
#define SIMU_STR_HLP_ACT_ENT QT_TRANSLATE_NOOP("SimulatedUIWidget", "<pre>[ ENT ]</pre>")
|
||||
#define SIMU_STR_HLP_ACT_UP QT_TRANSLATE_NOOP("SimulatedUIWidget", "<pre>[ UP ]</pre>")
|
||||
#define SIMU_STR_HLP_ACT_DN QT_TRANSLATE_NOOP("SimulatedUIWidget", "<pre>[ DN ]</pre>")
|
||||
#define SIMU_STR_HLP_ACT_PLS QT_TRANSLATE_NOOP("SimulatedUIWidget", "<pre>[ <font size=+2>+</font> ]</pre>")
|
||||
#define SIMU_STR_HLP_ACT_MIN QT_TRANSLATE_NOOP("SimulatedUIWidget", "<pre>[ <font size=+2>-</font> ]</pre>")
|
||||
#define SIMU_STR_HLP_ACT_PGUP QT_TRANSLATE_NOOP("SimulatedUIWidget", "<pre>[ PgUp ]</pre>")
|
||||
#define SIMU_STR_HLP_ACT_PGDN QT_TRANSLATE_NOOP("SimulatedUIWidget", "<pre>[ PgDn ]</pre>")
|
||||
#define SIMU_STR_HLP_ACT_MDL QT_TRANSLATE_NOOP("SimulatedUIWidget", "<pre>[ MDL ]</pre>")
|
||||
#define SIMU_STR_HLP_ACT_RTN QT_TRANSLATE_NOOP("SimulatedUIWidget", "<pre>[ RTN ]</pre>")
|
||||
#define SIMU_STR_HLP_ACT_SYS QT_TRANSLATE_NOOP("SimulatedUIWidget", "<pre>[ SYS ]</pre>")
|
||||
#define SIMU_STR_HLP_ACT_TELE QT_TRANSLATE_NOOP("SimulatedUIWidget", "<pre>[ TELE ]</pre>")
|
||||
#define SIMU_STR_HLP_ACT_MENU_ICN QT_TRANSLATE_NOOP("SimulatedUIWidget", "<font size=+3>≡</font>") // ≡
|
||||
#define SIMU_STR_HLP_ACT_MENU QCoreApplication::translate("SimulatedUIWidget", "<pre>[ MENU ]</pre>")
|
||||
#define SIMU_STR_HLP_ACT_PAGE QCoreApplication::translate("SimulatedUIWidget", "<pre>[ PAGE ]</pre>")
|
||||
#define SIMU_STR_HLP_ACT_EXIT QCoreApplication::translate("SimulatedUIWidget", "<pre>[ EXIT ]</pre>")
|
||||
#define SIMU_STR_HLP_ACT_ENT QCoreApplication::translate("SimulatedUIWidget", "<pre>[ ENT ]</pre>")
|
||||
#define SIMU_STR_HLP_ACT_UP QCoreApplication::translate("SimulatedUIWidget", "<pre>[ UP ]</pre>")
|
||||
#define SIMU_STR_HLP_ACT_DN QCoreApplication::translate("SimulatedUIWidget", "<pre>[ DN ]</pre>")
|
||||
#define SIMU_STR_HLP_ACT_PLS QCoreApplication::translate("SimulatedUIWidget", "<pre>[ <font size=+2>+</font> ]</pre>")
|
||||
#define SIMU_STR_HLP_ACT_MIN QCoreApplication::translate("SimulatedUIWidget", "<pre>[ <font size=+2>-</font> ]</pre>")
|
||||
#define SIMU_STR_HLP_ACT_PGUP QCoreApplication::translate("SimulatedUIWidget", "<pre>[ PgUp ]</pre>")
|
||||
#define SIMU_STR_HLP_ACT_PGDN QCoreApplication::translate("SimulatedUIWidget", "<pre>[ PgDn ]</pre>")
|
||||
#define SIMU_STR_HLP_ACT_MDL QCoreApplication::translate("SimulatedUIWidget", "<pre>[ MDL ]</pre>")
|
||||
#define SIMU_STR_HLP_ACT_RTN QCoreApplication::translate("SimulatedUIWidget", "<pre>[ RTN ]</pre>")
|
||||
#define SIMU_STR_HLP_ACT_SYS QCoreApplication::translate("SimulatedUIWidget", "<pre>[ SYS ]</pre>")
|
||||
#define SIMU_STR_HLP_ACT_TELE QCoreApplication::translate("SimulatedUIWidget", "<pre>[ TELE ]</pre>")
|
||||
#define SIMU_STR_HLP_ACT_MENU_ICN QCoreApplication::translate("SimulatedUIWidget", "<font size=+3>≡</font>") // ≡
|
||||
|
||||
|
||||
#define SIMU_STR_HLP_KEYS_EXIT SIMU_STR_HLP_KEY_DEL "|" SIMU_STR_HLP_KEY_BKSP "|" SIMU_STR_HLP_KEY_ESC
|
||||
#define SIMU_STR_HLP_KEYS_ACTIVATE SIMU_STR_HLP_KEY_ENTER "|" SIMU_STR_HLP_MOUSE_MID
|
||||
#define SIMU_STR_HLP_KEYS_GO_UP SIMU_STR_HLP_KEY_UP "|" SIMU_STR_HLP_KEY_PGUP
|
||||
#define SIMU_STR_HLP_KEYS_GO_DN SIMU_STR_HLP_KEY_DN "|" SIMU_STR_HLP_KEY_PGDN
|
||||
#define SIMU_STR_HLP_KEYS_GO_LFT SIMU_STR_HLP_KEY_LFT "|" SIMU_STR_HLP_KEY_MIN "|" SIMU_STR_HLP_MOUSE_UP
|
||||
#define SIMU_STR_HLP_KEYS_GO_RGT SIMU_STR_HLP_KEY_RGT "|" SIMU_STR_HLP_KEY_PLS "|" SIMU_STR_HLP_MOUSE_DN
|
||||
#define SIMU_STR_HLP_KEYS_EXIT SIMU_STR_HLP_KEY_DEL % "|" % SIMU_STR_HLP_KEY_BKSP % "|" % SIMU_STR_HLP_KEY_ESC
|
||||
#define SIMU_STR_HLP_KEYS_ACTIVATE SIMU_STR_HLP_KEY_ENTER % "|" % SIMU_STR_HLP_MOUSE_MID
|
||||
#define SIMU_STR_HLP_KEYS_GO_UP SIMU_STR_HLP_KEY_UP % "|" % SIMU_STR_HLP_KEY_PGUP
|
||||
#define SIMU_STR_HLP_KEYS_GO_DN SIMU_STR_HLP_KEY_DN % "|" % SIMU_STR_HLP_KEY_PGDN
|
||||
#define SIMU_STR_HLP_KEYS_GO_LFT SIMU_STR_HLP_KEY_LFT % "|" % SIMU_STR_HLP_KEY_MIN % "|" % SIMU_STR_HLP_MOUSE_UP
|
||||
#define SIMU_STR_HLP_KEYS_GO_RGT SIMU_STR_HLP_KEY_RGT % "|" % SIMU_STR_HLP_KEY_PLS % "|" % SIMU_STR_HLP_MOUSE_DN
|
||||
|
||||
#define SIMU_STR_HLP_ACT_ROT_LFT SIMU_STR_HLP_ROTENC " " SIMU_STR_HLP_ROTENC_LFT
|
||||
#define SIMU_STR_HLP_ACT_ROT_RGT SIMU_STR_HLP_ROTENC " " SIMU_STR_HLP_ROTENC_RGT
|
||||
#define SIMU_STR_HLP_ACT_ROT_DN SIMU_STR_HLP_ROTENC " " SIMU_STR_HLP_ROTENC_DN
|
||||
#define SIMU_STR_HLP_ACT_ROT_LFT SIMU_STR_HLP_ROTENC % " " % SIMU_STR_HLP_ROTENC_LFT
|
||||
#define SIMU_STR_HLP_ACT_ROT_RGT SIMU_STR_HLP_ROTENC % " " % SIMU_STR_HLP_ROTENC_RGT
|
||||
#define SIMU_STR_HLP_ACT_ROT_DN SIMU_STR_HLP_ROTENC % " " % SIMU_STR_HLP_ROTENC_DN
|
||||
|
||||
#endif // SIMULATOR_STRINGS_H
|
||||
|
||||
@@ -227,7 +227,7 @@ void SimulatorStartupDialog::onRadioTypeChanged(int index)
|
||||
|
||||
void SimulatorStartupDialog::onDataFileSelect(bool)
|
||||
{
|
||||
QString filter = tr(EEPROM_FILES_FILTER) + tr("All files (*.*)");
|
||||
QString filter = EEPROM_FILES_FILTER % tr("All files (*.*)");
|
||||
QString file = QFileDialog::getSaveFileName(this, QObject::tr("Select a data file"), ui->dataFile->text(),
|
||||
filter, NULL, QFileDialog::DontConfirmOverwrite);
|
||||
if (!file.isEmpty()) {
|
||||
|
||||
@@ -557,9 +557,15 @@ void AppData::init()
|
||||
{
|
||||
qRegisterMetaTypeStreamOperators<SimulatorOptions>("SimulatorOptions");
|
||||
|
||||
firstUse = false;
|
||||
upgradeFromVersion = "";
|
||||
|
||||
QSettings settings(COMPANY, PRODUCT);
|
||||
if (!settings.contains("settings_version"))
|
||||
importSettings(settings);
|
||||
if (!settings.contains("settings_version")) {
|
||||
if (!importSettings(settings))
|
||||
firstUse = true;
|
||||
}
|
||||
convertSettings(settings);
|
||||
|
||||
// Initialize the profiles
|
||||
for (int i=0; i<MAX_PROFILES; i++)
|
||||
@@ -649,23 +655,69 @@ QMap<int, QString> AppData::getActiveProfiles()
|
||||
return active;
|
||||
}
|
||||
|
||||
void AppData::convertSettings(QSettings & settings)
|
||||
{
|
||||
// convert old settings to new
|
||||
if (settings.contains("useWizard")) {
|
||||
if (!settings.contains("newModelAction")) {
|
||||
newModelAction(settings.value("useWizard").toBool() ? 1 : 2);
|
||||
}
|
||||
settings.remove("useWizard");
|
||||
}
|
||||
if (settings.contains("warningId") && settings.value("warningId").toInt() == 7) {
|
||||
// meaning of warningId changed during v2.2 development but value of "7" indicates old setting, removing it will restore defaults
|
||||
settings.remove("warningId");
|
||||
}
|
||||
}
|
||||
|
||||
bool AppData::importSettings(QSettings & toSettings)
|
||||
{
|
||||
QSettings * fromSettings = NULL;
|
||||
|
||||
QSettings settings21("OpenTX", "Companion 2.1");
|
||||
QSettings settings20("OpenTX", "Companion 2.0");
|
||||
QSettings settings16("OpenTX", "OpenTX Companion");
|
||||
QSettings settings9x("companion9x", "companion9x");
|
||||
|
||||
if (settings21.contains("settings_version"))
|
||||
if (settings21.contains("settings_version")) {
|
||||
fromSettings = &settings21;
|
||||
else if (settings20.contains("settings_version"))
|
||||
fromSettings = &settings20;
|
||||
else if (settings16.contains("settings_version"))
|
||||
fromSettings = &settings16;
|
||||
else if (settings9x.contains("default_mode"))
|
||||
fromSettings = &settings9x;
|
||||
upgradeFromVersion = "2.1";
|
||||
}
|
||||
else {
|
||||
settings21.clear();
|
||||
}
|
||||
|
||||
if (!fromSettings) {
|
||||
QSettings settings20("OpenTX", "Companion 2.0");
|
||||
if (settings20.contains("settings_version")) {
|
||||
fromSettings = &settings20;
|
||||
upgradeFromVersion = "2.0";
|
||||
}
|
||||
else {
|
||||
settings20.clear();
|
||||
}
|
||||
}
|
||||
|
||||
if (!fromSettings) {
|
||||
QSettings settings16("OpenTX", "OpenTX Companion");
|
||||
if (settings16.contains("settings_version")) {
|
||||
fromSettings = &settings16;
|
||||
upgradeFromVersion = "1.x";
|
||||
}
|
||||
else {
|
||||
settings16.clear();
|
||||
}
|
||||
}
|
||||
|
||||
if (!fromSettings) {
|
||||
QSettings settings9x("companion9x", "companion9x");
|
||||
if (settings9x.contains("default_mode")) {
|
||||
fromSettings = &settings9x;
|
||||
upgradeFromVersion = "Companion9X";
|
||||
}
|
||||
else {
|
||||
settings9x.clear();
|
||||
}
|
||||
}
|
||||
|
||||
if (!fromSettings)
|
||||
return false;
|
||||
|
||||
// do not copy these settings
|
||||
QStringList excludeKeys = QStringList() << "compilation-server";
|
||||
@@ -677,16 +729,14 @@ bool AppData::importSettings(QSettings & toSettings)
|
||||
#endif
|
||||
|
||||
// import settings
|
||||
if (fromSettings) {
|
||||
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 && fromSettings->applicationName() == "companion9x") {
|
||||
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));
|
||||
@@ -726,20 +776,12 @@ bool AppData::importSettings(QSettings & toSettings)
|
||||
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 );
|
||||
}
|
||||
|
||||
// convert old settings to new
|
||||
|
||||
if (toSettings.contains("useWizard")) {
|
||||
if (!toSettings.contains("newModelAction")) {
|
||||
newModelAction(toSettings.value("useWizard").toBool() ? 1 : 2);
|
||||
}
|
||||
toSettings.remove("useWizard");
|
||||
}
|
||||
|
||||
return fromSettings ? true : false;
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -429,10 +429,15 @@ class AppData: protected CompStoreObj
|
||||
void init();
|
||||
|
||||
QMap<int, QString> getActiveProfiles();
|
||||
inline bool isFirstUse() const { return firstUse; }
|
||||
inline QString previousVersion() const { return upgradeFromVersion; }
|
||||
|
||||
protected:
|
||||
void convertSettings(QSettings & settings);
|
||||
bool importSettings(QSettings & toSettings);
|
||||
|
||||
bool firstUse;
|
||||
QString upgradeFromVersion;
|
||||
};
|
||||
|
||||
extern AppData g;
|
||||
|
||||
@@ -89,6 +89,7 @@ bool CategorizedStorageFormat::load(RadioData & radioData)
|
||||
radioData.models.resize(modelIndex + 1);
|
||||
}
|
||||
if (!loadModelFromByteArray(radioData.models[modelIndex], modelBuffer)) {
|
||||
setError(QObject::tr("Error loading models"));
|
||||
return false;
|
||||
}
|
||||
strncpy(radioData.models[modelIndex].filename, qPrintable(fileName), sizeof(radioData.models[modelIndex].filename));
|
||||
|
||||
+2695
-2405
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@@ -20,9 +20,33 @@
|
||||
|
||||
#ifndef _WARNINGS_H_
|
||||
#define _WARNINGS_H_
|
||||
#define WARNING_LEVEL 0
|
||||
#define WARNING_ID 7
|
||||
#define WARNING QObject::tr("Thank you for upgrading to OpenTX 2.0. This is a major upgrade that adds and modifies a lot of things, so please make sure that you read release notes carefully to learn about the changes, and thoroughly check each of your models for proper function.\n\nThe OpenTX Team.")
|
||||
|
||||
#define CPN_STR_MSG_WELCOME QCoreApplication::translate("Companion", \
|
||||
"<p><b>Welcome to OpenTX v%1.</b></p>" \
|
||||
"<p>As the first step, please configure the initial Radio Profile by selecting your Radio Type, Menu Language, and Build Options.</p>" \
|
||||
"<p>You may also want to take this time to review the other available options in the displayed Settings dialog.</p>" \
|
||||
"<p>After saving your settings, we recommend you download the latest firmware for your radio by using the <i>File -> Download</i> menu option.</p>" \
|
||||
"<p>Please visit <a href='http://www.open-tx.org'>open-tx.org</a> for latest news, updates and documentation. Thank you for choosing OpenTX!</p>" \
|
||||
"- The OpenTX Team.")
|
||||
|
||||
#define CPN_STR_MSG_UPGRADED QCoreApplication::translate("Companion", \
|
||||
"<p><b>Thank you for upgrading to OpenTX v%1.</b></p>" \
|
||||
"<p>This is a major upgrade that adds and modifies a lot of things, so please make sure that you read release notes carefully" \
|
||||
" to learn about the changes, and thoroughly check each of your models for proper function.</p>" \
|
||||
"<p>Please visit <a href='http://www.open-tx.org'>open-tx.org</a> for release notes and other documentation.</p>" \
|
||||
"- The OpenTX Team.")
|
||||
|
||||
namespace AppMessages {
|
||||
|
||||
// These are used for saving "[don't] show this message again" user preferences.
|
||||
enum MessageCodes {
|
||||
MSG_NONE = 0,
|
||||
MSG_WELCOME = 0x01,
|
||||
MSG_UPGRADED = 0x02,
|
||||
MSG_RESERVED = 0x04, // reserved due to legacy code
|
||||
};
|
||||
|
||||
} // namespace AppWarnings
|
||||
|
||||
#endif // _WARNINGS_H_
|
||||
|
||||
|
||||
@@ -1 +1 @@
|
||||
SUBSYSTEMS=="usb", ATTRS{idVendor}=="0483", ATTRS{idProduct}=="df11", MODE:="0666";
|
||||
SUBSYSTEMS=="usb", ATTRS{idVendor}=="0483", ATTRS{idProduct}=="df11", MODE:="0666"
|
||||
|
||||
@@ -208,6 +208,7 @@ Section "Uninstall"
|
||||
Delete "$INSTDIR\Qt5Network.dll"
|
||||
Delete "$INSTDIR\Qt5Multimedia.dll"
|
||||
Delete "$INSTDIR\Qt5Xml.dll"
|
||||
Delete "$INSTDIR\Qt5Svg.dll"
|
||||
Delete "$INSTDIR\avrdude.exe"
|
||||
Delete "$INSTDIR\avrdude.conf"
|
||||
Delete "$INSTDIR\libusb0.dll"
|
||||
@@ -220,7 +221,7 @@ Section "Uninstall"
|
||||
Delete "$INSTDIR\platforms\*.*"
|
||||
Delete "$INSTDIR\printsupport\*.*"
|
||||
Delete "$INSTDIR\mediaservice\*.*"
|
||||
Delete "$INSTDIR\mediaservice\imageformats\*.*"
|
||||
Delete "$INSTDIR\imageformats\*.*"
|
||||
|
||||
RMDir "$INSTDIR\lang"
|
||||
RMDir "$INSTDIR\phonon_backend"
|
||||
|
||||
@@ -16,6 +16,6 @@ Homepage: http://www.open-tx.org/
|
||||
|
||||
Package: opentx-companion22
|
||||
Architecture: any
|
||||
Depends: ${shlibs:Depends}
|
||||
Depends: ${shlibs:Depends}, libqt5multimedia5-plugins
|
||||
Description: OpenTX Companion
|
||||
Models and settings editor for the OpenTX open source firmware
|
||||
|
||||
+31
-1
@@ -3,9 +3,30 @@ set -e
|
||||
set -x
|
||||
|
||||
# $1 is distribution "trusty" OR "yakkety"
|
||||
#
|
||||
# Option "-n" or "--nightly" can be used to configure build script to produce a Companion with DALLOW_NIGHTLY_BUILDS=YES flag
|
||||
|
||||
|
||||
cd `dirname ${0}`
|
||||
|
||||
nightly_build=0
|
||||
|
||||
while [ $# -gt 0 ]
|
||||
do
|
||||
case "$1" in
|
||||
--nightly*)
|
||||
nightly_build=1;;
|
||||
-n*)
|
||||
nightly_build=1;;
|
||||
-*)
|
||||
echo >&2 "usage: $0 [-n|--nightly] DISTRO"
|
||||
exit 1;;
|
||||
*)
|
||||
break;; # terminate while loop
|
||||
esac
|
||||
shift
|
||||
done
|
||||
|
||||
|
||||
distro=${1%/}
|
||||
|
||||
@@ -32,10 +53,19 @@ cp ${distro}/* ../debian/
|
||||
echo "Editing rules to set version suffix to \"${suffix}\""
|
||||
sed -i "s/__VERSION_SUFFIX__/${suffix}/g" ../debian/rules
|
||||
|
||||
if [ ${nightly_build} -gt 0 ] ; then
|
||||
echo "Setting nightly build flag"
|
||||
sed -i "s/DALLOW_NIGHTLY_BUILDS=YES/DALLOW_NIGHTLY_BUILDS=YES/g" ../debian/rules
|
||||
else
|
||||
sed -i "s/DALLOW_NIGHTLY_BUILDS=YES/DALLOW_NIGHTLY_BUILDS=NO/g" ../debian/rules
|
||||
fi
|
||||
|
||||
# remove old package and prepare new one
|
||||
cd ..
|
||||
rm -f ../opentx-companion22_*${distro}*
|
||||
debuild -S -sa -I -Ijenkins -Ilaunchpad -Idoc -Ibuild -I*.luac
|
||||
|
||||
echo "Use this command to upload to launchpad:"
|
||||
echo "Use this command to upload to launchpad (nightly builds):"
|
||||
echo " dput ppa:opentx-test/ppa opentx-companion22_<version>.changes"
|
||||
echo "OR releases:"
|
||||
echo " dput ppa:opentx-test/rel opentx-companion22_<version>.changes"
|
||||
|
||||
@@ -1,3 +1,9 @@
|
||||
opentx-companion22 (2.2.0~N371~trusty) trusty; urgency=low
|
||||
|
||||
* New release 2.2.0~N371 RC18
|
||||
|
||||
-- projectkk2glider <projectkk2glider@gmail.com> Sat, 29 Apr 2017 18:57:42 +0200
|
||||
|
||||
opentx-companion22 (2.2.0~N370~trusty) trusty; urgency=low
|
||||
|
||||
* New release 2.2.0~N370 RC17
|
||||
|
||||
@@ -1,3 +1,9 @@
|
||||
opentx-companion22 (2.2.0~N371~xenial) xenial; urgency=low
|
||||
|
||||
* New release 2.2.0~N371 RC18
|
||||
|
||||
-- projectkk2glider <projectkk2glider@gmail.com> Sat, 29 Apr 2017 18:57:37 +0200
|
||||
|
||||
opentx-companion22 (2.2.0~N370~xenial) xenial; urgency=low
|
||||
|
||||
* New release 2.2.0~N370 RC17
|
||||
|
||||
@@ -1,3 +1,9 @@
|
||||
opentx-companion22 (2.2.0~N371~yakkety) yakkety; urgency=low
|
||||
|
||||
* New release 2.2.0~N371 RC18
|
||||
|
||||
-- projectkk2glider <projectkk2glider@gmail.com> Sat, 29 Apr 2017 18:57:47 +0200
|
||||
|
||||
opentx-companion22 (2.2.0~N370~yakkety) yakkety; urgency=low
|
||||
|
||||
* New release 2.2.0~N370 RC17
|
||||
|
||||
@@ -16,16 +16,13 @@ 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" } },
|
||||
@@ -269,53 +266,12 @@ local function runSettingsPage(event)
|
||||
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
|
||||
|
||||
|
||||
Executable
+340
@@ -0,0 +1,340 @@
|
||||
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 }
|
||||
@@ -0,0 +1,283 @@
|
||||
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 }
|
||||
+16
-1
@@ -26,6 +26,7 @@ uint8_t s_curveChan;
|
||||
int8_t * curveEnd[MAX_CURVES];
|
||||
void loadCurves()
|
||||
{
|
||||
bool showWarning= false;
|
||||
int8_t * tmp = g_model.points;
|
||||
for (int i=0; i<MAX_CURVES; i++) {
|
||||
switch (g_model.curves[i].type) {
|
||||
@@ -41,7 +42,21 @@ void loadCurves()
|
||||
tmp += 5+g_model.curves[i].points;
|
||||
break;
|
||||
}
|
||||
// Older version did not check if we exceeded the array
|
||||
int8_t * maxend = &g_model.points[MAX_CURVE_POINTS - 2*(MAX_CURVES-i-1)];
|
||||
if (tmp > maxend) {
|
||||
tmp = maxend;
|
||||
g_model.curves[i].type=CURVE_TYPE_STANDARD;
|
||||
g_model.curves[i].points=-3;
|
||||
showWarning=true;
|
||||
}
|
||||
curveEnd[i] = tmp;
|
||||
|
||||
}
|
||||
if (showWarning) {
|
||||
POPUP_WARNING("Invalid curve data repaired");
|
||||
const char * w = "check your curves, logic switches";
|
||||
SET_WARNING_INFO(w, strlen(w), 0);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -50,7 +65,7 @@ int8_t * curveAddress(uint8_t idx)
|
||||
return idx==0 ? g_model.points : curveEnd[idx-1];
|
||||
}
|
||||
|
||||
bool moveCurve(uint8_t index, int8_t shift) // TODO bool?
|
||||
bool moveCurve(uint8_t index, int8_t shift)
|
||||
{
|
||||
if (curveEnd[MAX_CURVES-1] + shift > g_model.points + sizeof(g_model.points)) {
|
||||
AUDIO_WARNING2();
|
||||
|
||||
@@ -168,7 +168,7 @@ enum CurveType {
|
||||
#define LEN_INPUT_NAME 3
|
||||
#define LEN_CURVE_NAME 3
|
||||
#define LEN_FUNCTION_NAME 6
|
||||
#define MAX_CURVES 16
|
||||
#define MAX_CURVES 16 // TODO next EEPROM check if can be changed to 32 to have all ARM the same
|
||||
#define MAX_CURVE_POINTS 512
|
||||
#elif defined(PCBTARANIS)
|
||||
#define LEN_MODEL_NAME 12
|
||||
|
||||
@@ -367,7 +367,7 @@ PACK(struct FlightModeData {
|
||||
PACK(struct CurveData {
|
||||
uint8_t type:1;
|
||||
uint8_t smooth:1;
|
||||
int8_t points:6; // TODO conversion
|
||||
int8_t points:6; // describes number of points - 5
|
||||
NOBACKUP(char name[LEN_CURVE_NAME]);
|
||||
});
|
||||
#else
|
||||
|
||||
@@ -87,11 +87,12 @@ void menuModelCurveOne(event_t event)
|
||||
for (int i = 1; i < 4 + crv.points; i++) {
|
||||
points[i] = calcRESXto100(applyCustomCurve(calc100toRESX(getCurveX(5 + crv.points, i)), s_curveChan));
|
||||
}
|
||||
moveCurve(s_curveChan, checkIncDec_Ret > 0 ? 3 + crv.points : -3 - crv.points);
|
||||
if (newType == CURVE_TYPE_CUSTOM) {
|
||||
resetCustomCurveX(points, 5 + crv.points);
|
||||
if (moveCurve(s_curveChan, checkIncDec_Ret > 0 ? 3 + crv.points : -3 - crv.points)) {
|
||||
if (newType == CURVE_TYPE_CUSTOM) {
|
||||
resetCustomCurveX(points, 5 + crv.points);
|
||||
}
|
||||
crv.type = newType;
|
||||
}
|
||||
crv.type = newType;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -105,16 +106,17 @@ void menuModelCurveOne(event_t event)
|
||||
if (checkIncDec_Ret) {
|
||||
int8_t newPoints[MAX_POINTS_PER_CURVE];
|
||||
newPoints[0] = points[0];
|
||||
newPoints[4+count] = points[4+crv.points];
|
||||
for (int i=1; i<4+count; i++)
|
||||
newPoints[i] = calcRESXto100(applyCustomCurve(calc100toRESX(getCurveX(5+count, i)), s_curveChan));
|
||||
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)
|
||||
points[5+count+i-1] = getCurveX(5+count, i);
|
||||
newPoints[4 + count] = points[4 + crv.points];
|
||||
for (int i = 1; i < 4 + count; i++)
|
||||
newPoints[i] = calcRESXto100(applyCustomCurve(calc100toRESX(getCurveX(5 + count, i)), 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)
|
||||
points[5 + count + i - 1] = getCurveX(5 + count, i);
|
||||
}
|
||||
crv.points = count;
|
||||
}
|
||||
crv.points = count;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -366,8 +366,10 @@ void menuSpecialFunctions(event_t event, CustomFunctionData * functions, CustomF
|
||||
else if (func == FUNC_VOLUME) {
|
||||
val_max = MIXSRC_LAST_CH;
|
||||
drawSource(MODEL_SPECIAL_FUNC_3RD_COLUMN, y, val_displayed, attr);
|
||||
INCDEC_SET_FLAG(eeFlags | INCDEC_SOURCE);
|
||||
INCDEC_ENABLE_CHECK(isSourceAvailable);
|
||||
if (active) {
|
||||
INCDEC_SET_FLAG(eeFlags | INCDEC_SOURCE);
|
||||
INCDEC_ENABLE_CHECK(isSourceAvailable);
|
||||
}
|
||||
}
|
||||
#elif defined(VOICE)
|
||||
else if (func == FUNC_PLAY_TRACK) {
|
||||
@@ -421,8 +423,10 @@ void menuSpecialFunctions(event_t event, CustomFunctionData * functions, CustomF
|
||||
case FUNC_ADJUST_GVAR_SOURCE:
|
||||
val_max = MIXSRC_LAST_CH;
|
||||
drawSource(MODEL_SPECIAL_FUNC_3RD_COLUMN, y, val_displayed, attr);
|
||||
INCDEC_SET_FLAG(eeFlags | INCDEC_SOURCE);
|
||||
INCDEC_ENABLE_CHECK(isSourceAvailable);
|
||||
if (active) {
|
||||
INCDEC_SET_FLAG(eeFlags | INCDEC_SOURCE);
|
||||
INCDEC_ENABLE_CHECK(isSourceAvailable);
|
||||
}
|
||||
break;
|
||||
case FUNC_ADJUST_GVAR_GVAR:
|
||||
val_max = MAX_GVARS-1;
|
||||
|
||||
@@ -91,11 +91,12 @@ void menuModelCurveOne(event_t event)
|
||||
for (int i = 1; i < 4 + crv.points; i++) {
|
||||
points[i] = calcRESXto100(applyCustomCurve(calc100toRESX(getCurveX(5 + crv.points, i)), s_curveChan));
|
||||
}
|
||||
moveCurve(s_curveChan, checkIncDec_Ret > 0 ? 3 + crv.points : -3 - crv.points);
|
||||
if (newType == CURVE_TYPE_CUSTOM) {
|
||||
resetCustomCurveX(points, 5 + crv.points);
|
||||
if (moveCurve(s_curveChan, checkIncDec_Ret > 0 ? 3 + crv.points : -3 - crv.points)) {
|
||||
if (newType == CURVE_TYPE_CUSTOM) {
|
||||
resetCustomCurveX(points, 5 + crv.points);
|
||||
}
|
||||
crv.type = newType;
|
||||
}
|
||||
crv.type = newType;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -109,16 +110,17 @@ void menuModelCurveOne(event_t event)
|
||||
if (checkIncDec_Ret) {
|
||||
int8_t newPoints[MAX_POINTS_PER_CURVE];
|
||||
newPoints[0] = points[0];
|
||||
newPoints[4+count] = points[4+crv.points];
|
||||
for (int i=1; i<4+count; i++)
|
||||
newPoints[i] = calcRESXto100(applyCustomCurve(calc100toRESX(getCurveX(5+count, i)), s_curveChan));
|
||||
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)
|
||||
points[5+count+i-1] = getCurveX(5+count, i);
|
||||
newPoints[4 + count] = points[4 + crv.points];
|
||||
for (int i = 1; i < 4 + count; i++)
|
||||
newPoints[i] = calcRESXto100(applyCustomCurve(calc100toRESX(getCurveX(5 + count, i)), 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)
|
||||
points[5 + count + i - 1] = getCurveX(5 + count, i);
|
||||
}
|
||||
crv.points = count;
|
||||
}
|
||||
crv.points = count;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -117,14 +117,15 @@ bool menuModelCurveOne(event_t event)
|
||||
if (attr) {
|
||||
uint8_t newType = checkIncDecModelZero(event, crv.type, CURVE_TYPE_LAST);
|
||||
if (newType != crv.type) {
|
||||
for (int i=1; i<4+crv.points; i++) {
|
||||
for (int i = 1; i < 4 + crv.points; i++) {
|
||||
points[i] = calcRESXto100(applyCustomCurve(calc100toRESX(-100 + i * 200 / (4 + crv.points)), s_curveChan));
|
||||
}
|
||||
moveCurve(s_curveChan, checkIncDec_Ret > 0 ? 3+crv.points : -3-crv.points);
|
||||
if (newType == CURVE_TYPE_CUSTOM) {
|
||||
resetCustomCurveX(points, 5+crv.points);
|
||||
if (moveCurve(s_curveChan, checkIncDec_Ret > 0 ? 3 + crv.points : -3 - crv.points)) {
|
||||
if (newType == CURVE_TYPE_CUSTOM) {
|
||||
resetCustomCurveX(points, 5 + crv.points);
|
||||
}
|
||||
crv.type = newType;
|
||||
}
|
||||
crv.type = newType;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -140,13 +141,14 @@ bool menuModelCurveOne(event_t event)
|
||||
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));
|
||||
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)
|
||||
points[5+count+i-1] = -100 + (i*200) / (4+count);
|
||||
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)
|
||||
points[5 + count + i - 1] = -100 + (i * 200) / (4 + count);
|
||||
}
|
||||
crv.points = count;
|
||||
}
|
||||
crv.points = count;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -611,6 +611,7 @@ bool menuScreenSetup(int index, event_t event)
|
||||
}
|
||||
memset(&g_model.screenData[MAX_CUSTOM_SCREENS-1], 0, sizeof(CustomScreenData));
|
||||
customScreens[MAX_CUSTOM_SCREENS-1] = NULL;
|
||||
loadCustomScreens();
|
||||
killEvents(KEY_ENTER);
|
||||
chainMenu(menuTabScreensSetup[index > 0 ? index : 1]);
|
||||
return false;
|
||||
|
||||
@@ -21,9 +21,10 @@
|
||||
#include "opentx.h"
|
||||
|
||||
#define RECT_BORDER 1
|
||||
#define RECT_WIDTH (w - RECT_BORDER * 2)
|
||||
#define ROW_HEIGHT 17
|
||||
|
||||
#define VIEW_CHANNELS_LIMIT_PCT (g_model.extendedLimits ? LIMIT_EXT_PERCENT : 100)
|
||||
|
||||
class OutputsWidget: public Widget
|
||||
{
|
||||
public:
|
||||
@@ -34,40 +35,37 @@ class OutputsWidget: public Widget
|
||||
|
||||
virtual void refresh();
|
||||
|
||||
uint8_t drawChannels(uint16_t x, uint16_t y, uint16_t w, uint16_t h, uint8_t firstChan, bool bg_shown, uint16_t bg_color)
|
||||
uint8_t drawChannels(const uint16_t & x, const uint16_t & y, const uint16_t & w, const uint16_t & h, const uint8_t & firstChan, const bool & bg_shown, const uint16_t & bg_color)
|
||||
{
|
||||
char chanString[] = "CH32";
|
||||
uint8_t numChan = h / ROW_HEIGHT;
|
||||
uint8_t row_height = (h - numChan * ROW_HEIGHT >= numChan ? ROW_HEIGHT + 1 : ROW_HEIGHT);
|
||||
uint8_t lastChan = firstChan + numChan;
|
||||
const uint8_t numChan = h / ROW_HEIGHT;
|
||||
const uint8_t lastChan = firstChan + numChan;
|
||||
const uint8_t rowH = (h - numChan * ROW_HEIGHT >= numChan ? ROW_HEIGHT + 1 : ROW_HEIGHT);
|
||||
const uint16_t barW = w - RECT_BORDER * 2;
|
||||
const uint8_t barH = rowH - RECT_BORDER;
|
||||
const uint16_t barLft = x + RECT_BORDER;
|
||||
const uint16_t barMid = barLft + barW / 2;
|
||||
|
||||
for (uint8_t curChan = firstChan; curChan < lastChan && curChan <= MAX_OUTPUT_CHANNELS; curChan++) {
|
||||
const int16_t chanVal = calcRESXto100(channelOutputs[curChan-1]);
|
||||
const uint16_t rowTop = y + (curChan - firstChan) * rowH;
|
||||
const uint16_t barTop = rowTop + RECT_BORDER;
|
||||
const uint16_t fillW = divRoundClosest(barW * limit<int16_t>(0, abs(chanVal), VIEW_CHANNELS_LIMIT_PCT), VIEW_CHANNELS_LIMIT_PCT * 2);
|
||||
|
||||
for (uint8_t curChan = firstChan; curChan < lastChan && curChan < 33; curChan++) {
|
||||
int16_t chanVal = calcRESXto100(channelOutputs[curChan-1]);
|
||||
if (bg_shown) {
|
||||
lcdSetColor(bg_color);
|
||||
lcdDrawSolidFilledRect(x + RECT_BORDER, y + RECT_BORDER + (curChan - firstChan) * row_height, RECT_WIDTH , row_height - RECT_BORDER, CUSTOM_COLOR);
|
||||
lcdDrawSolidFilledRect(barLft, barTop, barW , barH, CUSTOM_COLOR);
|
||||
}
|
||||
if (chanVal > 0) {
|
||||
lcdDrawSolidFilledRect(x + RECT_BORDER + RECT_WIDTH / 2, y + RECT_BORDER + (curChan -firstChan) * row_height, divRoundClosest(RECT_WIDTH * chanVal, 200), row_height - RECT_BORDER, MAINVIEW_GRAPHICS_COLOR);
|
||||
if (fillW)
|
||||
lcdDrawSolidFilledRect((chanVal > 0 ? barMid : barMid - fillW), barTop, fillW, barH, MAINVIEW_GRAPHICS_COLOR);
|
||||
lcd->drawSolidVerticalLine(barMid, barTop, barH, MAINVIEW_GRAPHICS_COLOR);
|
||||
lcdDrawRect(x, rowTop, w, rowH + 1);
|
||||
lcdDrawNumber(x + barW - 10, barTop, chanVal, SMLSIZE | TEXT_COLOR | RIGHT, 0, NULL, "%");
|
||||
if (g_model.limitData[curChan - 1].name[0] != 0) {
|
||||
lcdDrawNumber(barLft + 1, barTop, curChan, SMLSIZE | TEXT_COLOR | LEFT | LEADING0, 2);
|
||||
lcdDrawSizedText(barLft + 23, barTop, g_model.limitData[curChan - 1].name, sizeof(g_model.limitData[curChan - 1].name), SMLSIZE | TEXT_COLOR | LEFT | ZCHAR);
|
||||
}
|
||||
else if (chanVal < 0) {
|
||||
uint16_t startpoint = x + RECT_BORDER;
|
||||
uint16_t endpoint = startpoint + RECT_WIDTH / 2;
|
||||
uint16_t size = divRoundClosest(- RECT_WIDTH * chanVal, 200);
|
||||
lcdDrawSolidFilledRect(endpoint - size, y + RECT_BORDER + (curChan - firstChan) * row_height, size, row_height - RECT_BORDER, MAINVIEW_GRAPHICS_COLOR);
|
||||
}
|
||||
lcd->drawSolidVerticalLine(x + RECT_BORDER + RECT_WIDTH / 2, y + RECT_BORDER + (curChan - firstChan) * row_height, row_height - RECT_BORDER, MAINVIEW_GRAPHICS_COLOR);
|
||||
lcdDrawRect(x, y + (curChan - firstChan) * row_height, w, row_height+1);
|
||||
lcdDrawNumber(x + RECT_WIDTH - 10, y + (curChan - firstChan) * row_height + 1, chanVal, SMLSIZE | TEXT_COLOR | RIGHT, 0, NULL, "%");
|
||||
if (g_model.limitData[curChan - 1].name[0] != 0) {
|
||||
strAppendSigned(chanString, curChan, 2);
|
||||
lcdDrawText(x + 2, y + (curChan - firstChan) * row_height + 1, chanString, SMLSIZE | TEXT_COLOR | LEFT);
|
||||
lcdDrawSizedText(x + 25, y + (curChan - firstChan) * row_height + 1, g_model.limitData[curChan - 1].name, sizeof(g_model.limitData[curChan - 1].name), SMLSIZE | TEXT_COLOR | LEFT | ZCHAR);
|
||||
}
|
||||
else {
|
||||
strAppend(chanString, "CH");
|
||||
strAppendSigned(&chanString[2], curChan, 2);
|
||||
lcdDrawText(x + 2, y + (curChan - firstChan) * row_height + 1, chanString, SMLSIZE | TEXT_COLOR | LEFT);
|
||||
putsChn(barLft + 1, barTop, curChan, SMLSIZE | TEXT_COLOR | LEFT);
|
||||
}
|
||||
}
|
||||
return lastChan - 1;
|
||||
|
||||
@@ -56,11 +56,11 @@ Return OpenTX version
|
||||
|
||||
@retval multiple (available since 2.1.7) returns 5 values:
|
||||
* (string) OpenTX version (ie "2.1.5")
|
||||
* (string) radio version: `taranisx9e`, `taranisplus` or `taranis`.
|
||||
* (string) radio version: `x9e`, `x9d+` or `x9d`.
|
||||
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) revison number (ie 5 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
|
||||
|
||||
@@ -108,6 +108,9 @@ Return the time since the radio was started in multiple of 10ms
|
||||
@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
|
||||
overflows will not happen.
|
||||
|
||||
@status current Introduced in 2.0.0
|
||||
*/
|
||||
static int luaGetTime(lua_State * L)
|
||||
@@ -304,7 +307,9 @@ bool luaFindFieldByName(const char * name, LuaField & field, unsigned int flags)
|
||||
/*luadoc
|
||||
@function sportTelemetryPop()
|
||||
|
||||
Pops a received SPORT packet from the queue. Please note that only packets using a data ID within 0x5000 to 0x52FF (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.
|
||||
Pops a received SPORT packet from the queue. Please note that only packets using a data ID within 0x5000 to 0x52FF
|
||||
(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:
|
||||
* sensor ID (number)
|
||||
|
||||
@@ -805,6 +805,9 @@ Get Curve parameters
|
||||
* `key` is point number (zero based)
|
||||
* `value` is x value
|
||||
|
||||
Note that functions returns the tables starting with index 0 contrary to LUA's
|
||||
usual index starting with 1
|
||||
|
||||
@status current Introduced in 2.0.12
|
||||
*/
|
||||
static int luaModelGetCurve(lua_State *L)
|
||||
@@ -849,6 +852,194 @@ static int luaModelGetCurve(lua_State *L)
|
||||
return 1;
|
||||
}
|
||||
|
||||
/*luadoc
|
||||
@function model.setCurve(curve, params)
|
||||
|
||||
Set Curve parameters
|
||||
|
||||
@param curve (unsigned number) curve number (use 0 for Curve1)
|
||||
|
||||
@param params see model.getCurve return format for table format. setCurve uses standard
|
||||
lua array indexing and array start at index 1
|
||||
|
||||
The first and last x value must 0 and 100 and x values must be monotonically increasing
|
||||
|
||||
@retval 0 - Everything okay
|
||||
1 - Wrong number of points
|
||||
2 - Invalid Curve number
|
||||
3 - Cuve does not fit anymore
|
||||
4 - point of out of index
|
||||
5 - x value not monotonically increasing
|
||||
6 - y value not in range [-100;100]
|
||||
7 - extra values for y are set
|
||||
8 - extra values for x are set
|
||||
|
||||
@status current Introduced in 2.2.0
|
||||
|
||||
Example setting a 4-point custom curve:
|
||||
```lua
|
||||
params = {}
|
||||
params["x"] = {0, 34, 77, 100}
|
||||
params["y"] = {-70, 20, -89, -100}
|
||||
params["smooth"] = 1
|
||||
params["type"] = 1
|
||||
val = model.setCurve(2, params)
|
||||
```
|
||||
setting a 6-point standard smoothed curve
|
||||
```lua
|
||||
val = model.setCurve(3, {smooth=1, y={-100, -50, 0, 50, 100, 80}})
|
||||
```
|
||||
|
||||
*/
|
||||
static int luaModelSetCurve(lua_State *L)
|
||||
{
|
||||
unsigned int curveIdx = luaL_checkunsigned(L, 1);
|
||||
|
||||
if (curveIdx >= MAX_CURVES) {
|
||||
lua_pushinteger(L, 2);
|
||||
return 1;
|
||||
}
|
||||
int8_t xPoints[MAX_POINTS_PER_CURVE];
|
||||
int8_t yPoints[MAX_POINTS_PER_CURVE];
|
||||
|
||||
// Init to invalid values
|
||||
memset(xPoints, -127, sizeof(xPoints));
|
||||
memset(yPoints, -127, sizeof(yPoints));
|
||||
|
||||
|
||||
CurveData &destCurveData = g_model.curves[curveIdx];
|
||||
CurveData newCurveData;
|
||||
memclear(&newCurveData, sizeof(CurveData));
|
||||
|
||||
luaL_checktype(L, -1, LUA_TTABLE);
|
||||
for (lua_pushnil(L); lua_next(L, -2); lua_pop(L, 1)) {
|
||||
luaL_checktype(L, -2, LUA_TSTRING); // key is string
|
||||
const char *key = luaL_checkstring(L, -2);
|
||||
if (!strcmp(key, "name")) {
|
||||
const char *name = luaL_checkstring(L, -1);
|
||||
str2zchar(newCurveData.name, name, sizeof(newCurveData.name));
|
||||
}
|
||||
else if (!strcmp(key, "type")) {
|
||||
newCurveData.type = luaL_checkinteger(L, -1);
|
||||
}
|
||||
else if (!strcmp(key, "smooth")) {
|
||||
newCurveData.smooth = luaL_checkinteger(L, -1);
|
||||
}
|
||||
else if (!strcmp(key, "x") || !strcmp(key, "y")) {
|
||||
luaL_checktype(L, -1, LUA_TTABLE);
|
||||
bool isX = !strcmp(key, "x");
|
||||
|
||||
for (lua_pushnil(L); lua_next(L, -2); lua_pop(L, 1)) {
|
||||
int idx = luaL_checkinteger(L, -2)-1;
|
||||
if (idx < 0 || idx > MAX_POINTS_PER_CURVE) {
|
||||
lua_pushinteger(L, 4);
|
||||
return 1;
|
||||
}
|
||||
int8_t val = luaL_checkinteger(L, -1);
|
||||
if (val < -100 || val > 100) {
|
||||
lua_pushinteger(L, 6);
|
||||
return 1;
|
||||
}
|
||||
if (isX)
|
||||
xPoints[idx] = val;
|
||||
else
|
||||
yPoints[idx] = val;
|
||||
}
|
||||
}
|
||||
}
|
||||
// Check how many points are set
|
||||
uint8_t numPoints=0;
|
||||
do {
|
||||
numPoints++;
|
||||
} while (yPoints[numPoints]!=-127 && numPoints < MAX_POINTS_PER_CURVE);
|
||||
newCurveData.points = numPoints - 5;
|
||||
|
||||
if (numPoints < MIN_POINTS_PER_CURVE || numPoints > MAX_POINTS_PER_CURVE) {
|
||||
lua_pushinteger(L, 1);
|
||||
return 1;
|
||||
}
|
||||
|
||||
if (newCurveData.type == CURVE_TYPE_CUSTOM) {
|
||||
|
||||
// The rest of the points are checked by the monotic condition
|
||||
for (unsigned int i=numPoints; i < sizeof(xPoints);i++)
|
||||
{
|
||||
if (xPoints[i] != -127)
|
||||
{
|
||||
lua_pushinteger(L, 8);
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
|
||||
// Check first and last point
|
||||
if (xPoints[0] != 0 || xPoints[newCurveData.points + 4] != 100) {
|
||||
lua_pushinteger(L, 5);
|
||||
return 1;
|
||||
}
|
||||
|
||||
// Check that x values are increasing
|
||||
for (int i = 1; i < numPoints; i++) {
|
||||
if (xPoints[i - 1] > xPoints[i]) {
|
||||
lua_pushinteger(L, 5);
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Check that ypoints have the right number of points set
|
||||
for (int i=0; i < 5 + newCurveData.points;i++)
|
||||
{
|
||||
if (yPoints[i] == -127)
|
||||
{
|
||||
lua_pushinteger(L, 7);
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
|
||||
// Calculate size of curve we replace
|
||||
int oldCurveMemSize;
|
||||
if (destCurveData.type == CURVE_TYPE_STANDARD) {
|
||||
oldCurveMemSize = 5 + destCurveData.points;
|
||||
}
|
||||
else {
|
||||
oldCurveMemSize = 8 + 2 * destCurveData.points;
|
||||
}
|
||||
|
||||
// Calculate own size
|
||||
int newCurveMemSize;
|
||||
if (newCurveData.type == CURVE_TYPE_STANDARD)
|
||||
newCurveMemSize = 5 + newCurveData.points;
|
||||
else
|
||||
newCurveMemSize = 8 + 2 * newCurveData.points;
|
||||
|
||||
int shift = newCurveMemSize - oldCurveMemSize;
|
||||
|
||||
// Also checks if new curve size would fit
|
||||
if (!moveCurve(curveIdx, shift)) {
|
||||
lua_pushinteger(L, 3);
|
||||
TRACE("curve shift is %d", shift);
|
||||
return 1;
|
||||
}
|
||||
|
||||
// Curve fits into mem, fill new curve
|
||||
destCurveData = newCurveData;
|
||||
|
||||
int8_t *point = curveAddress(curveIdx);
|
||||
for (int i = 0; i < destCurveData.points + 5; i++) {
|
||||
*point++ = yPoints[i];
|
||||
}
|
||||
|
||||
if (destCurveData.type == CURVE_TYPE_CUSTOM) {
|
||||
for (int i = 1; i < destCurveData.points + 4; i++) {
|
||||
*point++ = yPoints[i];
|
||||
}
|
||||
}
|
||||
storageDirty(EE_MODEL);
|
||||
|
||||
lua_pushinteger(L, 0);
|
||||
return 1;
|
||||
}
|
||||
|
||||
/*luadoc
|
||||
@function model.getCustomFunction(function)
|
||||
|
||||
@@ -1132,6 +1323,7 @@ const luaL_Reg modelLib[] = {
|
||||
{ "getCustomFunction", luaModelGetCustomFunction },
|
||||
{ "setCustomFunction", luaModelSetCustomFunction },
|
||||
{ "getCurve", luaModelGetCurve },
|
||||
{ "setCurve", luaModelSetCurve },
|
||||
{ "getOutput", luaModelGetOutput },
|
||||
{ "setOutput", luaModelSetOutput },
|
||||
{ "getGlobalVariable", luaModelGetGlobalVariable },
|
||||
|
||||
@@ -31,6 +31,7 @@
|
||||
lua_State *lsWidgets = NULL;
|
||||
extern int custom_lua_atpanic(lua_State *L);
|
||||
|
||||
#define LUA_WIDGET_FILENAME "/main.lua"
|
||||
#define LUA_FULLPATH_MAXLEN (LEN_FILE_PATH_MAX + LEN_SCRIPT_FILENAME + LEN_FILE_EXTENSION_MAX) // max length (example: /SCRIPTS/THEMES/mytheme.lua)
|
||||
|
||||
void exec(int function, int nresults=0)
|
||||
@@ -496,9 +497,10 @@ void luaLoadFiles(const char * directory, void (*callback)())
|
||||
res = f_readdir(&dir, &fno); /* Read a directory item */
|
||||
if (res != FR_OK || fno.fname[0] == 0) break; /* Break on error or end of dir */
|
||||
uint8_t len = strlen(fno.fname);
|
||||
if (len > 0 && fno.fname[0]!='.' && (fno.fattrib & AM_DIR)) {
|
||||
if (len > 0 && (unsigned int)(len + pathlen + sizeof(LUA_WIDGET_FILENAME)) <= sizeof(path) &&
|
||||
fno.fname[0]!='.' && (fno.fattrib & AM_DIR)) {
|
||||
strcpy(&path[pathlen], fno.fname);
|
||||
strcat(&path[pathlen], "/main.lua");
|
||||
strcat(&path[pathlen], LUA_WIDGET_FILENAME);
|
||||
if (isFileAvailable(path)) {
|
||||
luaLoadFile(path, callback);
|
||||
}
|
||||
|
||||
+4
-1
@@ -128,6 +128,7 @@ uint16_t isqrt32(uint32_t n)
|
||||
*/
|
||||
|
||||
#if defined(FRSKY_HUB) && !defined(CPUARM)
|
||||
// convert latitude and longitude to 1/10^6 degrees
|
||||
void extractLatitudeLongitude(uint32_t * latitude, uint32_t * longitude)
|
||||
{
|
||||
div_t qr = div(telemetryData.hub.gpsLatitude_bp, 100);
|
||||
@@ -140,10 +141,12 @@ void extractLatitudeLongitude(uint32_t * latitude, uint32_t * longitude)
|
||||
void getGpsPilotPosition()
|
||||
{
|
||||
extractLatitudeLongitude(&telemetryData.hub.pilotLatitude, &telemetryData.hub.pilotLongitude);
|
||||
// distFromEarthAxis = cos(lat) * EARTH_RADIUS
|
||||
// 1 - x2/2 + x4/24
|
||||
uint32_t lat = telemetryData.hub.pilotLatitude / 10000;
|
||||
uint32_t angle2 = (lat*lat) / 10000;
|
||||
uint32_t angle4 = angle2 * angle2;
|
||||
telemetryData.hub.distFromEarthAxis = 139*(((uint32_t)10000000-((angle2*(uint32_t)123370)/81)+(angle4/25))/12500);
|
||||
telemetryData.hub.distFromEarthAxis = 139 * (((uint32_t)10000000-((angle2*(uint32_t)123370)/81)+(angle4/25)) / 12500);
|
||||
// TRACE("telemetryData.hub.distFromEarthAxis=%d", telemetryData.hub.distFromEarthAxis);
|
||||
}
|
||||
|
||||
|
||||
+1
-1
@@ -1557,7 +1557,7 @@ extern uint8_t s_frsky_view;
|
||||
#endif
|
||||
|
||||
#define EARTH_RADIUSKM ((uint32_t)6371)
|
||||
#define EARTH_RADIUS ((uint32_t)111194)
|
||||
#define EARTH_RADIUS ((uint32_t)111194) // meters * pi / 180°
|
||||
|
||||
void getGpsPilotPosition();
|
||||
void getGpsDistance();
|
||||
|
||||
@@ -134,7 +134,7 @@ void pxxPutPcmTail(uint8_t port)
|
||||
#else
|
||||
void pxxPutPcmPart(uint8_t port, uint8_t value)
|
||||
{
|
||||
pulse_duration_t duration = value ? 48 : 32;
|
||||
pulse_duration_t duration = value ? 47 : 31;
|
||||
*modulePulsesData[port].pxx.ptr++ = duration;
|
||||
modulePulsesData[port].pxx.rest -= duration + 1;
|
||||
}
|
||||
|
||||
+14
-13
@@ -163,14 +163,14 @@ char * getTimerString(char * dest, putstime_t tme, uint8_t hours)
|
||||
{
|
||||
char * s = dest;
|
||||
div_t qr;
|
||||
|
||||
|
||||
if (tme < 0) {
|
||||
tme = -tme;
|
||||
*s++ = '-';
|
||||
}
|
||||
|
||||
|
||||
qr = div((int)tme, 60);
|
||||
|
||||
|
||||
if (hours) {
|
||||
div_t qr2 = div(qr.quot, 60);
|
||||
*s++ = '0' + (qr2.quot / 10);
|
||||
@@ -178,14 +178,14 @@ char * getTimerString(char * dest, putstime_t tme, uint8_t hours)
|
||||
*s++ = ':';
|
||||
qr.quot = qr2.rem;
|
||||
}
|
||||
|
||||
|
||||
*s++ = '0' + (qr.quot / 10);
|
||||
*s++ = '0' + (qr.quot % 10);
|
||||
*s++ = ':';
|
||||
*s++ = '0' + (qr.rem / 10);
|
||||
*s++ = '0' + (qr.rem % 10);
|
||||
*s = '\0';
|
||||
|
||||
|
||||
return dest;
|
||||
}
|
||||
|
||||
@@ -194,18 +194,18 @@ char * getCurveString(char * dest, int idx)
|
||||
if (idx == 0) {
|
||||
return getStringAtIndex(dest, STR_MMMINV, 0);
|
||||
}
|
||||
|
||||
|
||||
char * s = dest;
|
||||
if (idx < 0) {
|
||||
*s++ = '!';
|
||||
idx = -idx;
|
||||
}
|
||||
|
||||
|
||||
if (ZEXIST(g_model.curves[idx - 1].name))
|
||||
zchar2str(s, g_model.curves[idx - 1].name, LEN_CURVE_NAME);
|
||||
else
|
||||
strAppendStringWithIndex(s, STR_CV, idx);
|
||||
|
||||
|
||||
return dest;
|
||||
}
|
||||
|
||||
@@ -233,13 +233,13 @@ char * getSwitchString(char * dest, swsrc_t idx)
|
||||
else if (idx == SWSRC_OFF) {
|
||||
return getStringAtIndex(dest, STR_OFFON, 0);
|
||||
}
|
||||
|
||||
|
||||
char * s = dest;
|
||||
if (idx < 0) {
|
||||
*s++ = '!';
|
||||
idx = -idx;
|
||||
}
|
||||
|
||||
|
||||
#if defined(PCBSKY9X)
|
||||
#define IDX_TRIMS_IN_STR_VSWITCHES (1+SWSRC_LAST_SWITCH)
|
||||
#define IDX_ON_IN_STR_VSWITCHES (IDX_TRIMS_IN_STR_VSWITCHES+SWSRC_LAST_TRIM-SWSRC_FIRST_TRIM+2)
|
||||
@@ -294,7 +294,8 @@ char * getSwitchString(char * dest, swsrc_t idx)
|
||||
#endif
|
||||
|
||||
else if (idx <= SWSRC_LAST_LOGICAL_SWITCH) {
|
||||
strAppendStringWithIndex(s, "L", idx-SWSRC_FIRST_LOGICAL_SWITCH+1);
|
||||
*s++ = 'L';
|
||||
strAppendUnsigned(s, idx-SWSRC_FIRST_LOGICAL_SWITCH+1, 2);
|
||||
}
|
||||
else if (idx <= SWSRC_ONE) {
|
||||
getStringAtIndex(s, STR_VSWITCHES, IDX_ON_IN_STR_VSWITCHES + idx - SWSRC_ON);
|
||||
@@ -325,7 +326,7 @@ char * getSourceString(char * dest, mixsrc_t idx)
|
||||
dest[LEN_INPUT_NAME] = '\0';
|
||||
}
|
||||
else {
|
||||
strAppendUnsigned(dest, idx, 2);
|
||||
strAppendUnsigned(dest, idx+1, 2);
|
||||
}
|
||||
}
|
||||
#if defined(LUA_INPUTS)
|
||||
@@ -389,7 +390,7 @@ char * getSourceString(char * dest, mixsrc_t idx)
|
||||
if (qr.rem) dest[pos++] = (qr.rem==2 ? '+' : '-');
|
||||
dest[pos] = '\0';
|
||||
}
|
||||
|
||||
|
||||
return dest;
|
||||
}
|
||||
#endif
|
||||
|
||||
@@ -93,7 +93,7 @@ elseif(TELEMETRY STREQUAL MAVLINK)
|
||||
WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR})
|
||||
if(NOT ${GIT_SUBMODULE_RESULT} EQUAL 0)
|
||||
message(FATAL_ERROR "Error: Cannot clone submodule at ${THIRDPARTY_DIR}/GCS_MAVLink/include_v1.0
|
||||
If you downloaded this project as a ZIP file, please instead run
|
||||
If you downloaded this project as a ZIP file, please instead run
|
||||
'git clone --recursive https://github.com/opentx/opentx.git'")
|
||||
endif()
|
||||
endif()
|
||||
@@ -106,7 +106,6 @@ If you downloaded this project as a ZIP file, please instead run
|
||||
math(EXPR EEPROM_VARIANT ${EEPROM_VARIANT}+${MAVLINK_VARIANT})
|
||||
elseif(TELEMETRY STREQUAL TELEMETREZ)
|
||||
add_definitions(-DTELEMETRY_TELEMETREZ)
|
||||
set(SRC ${SRC} telemetry/jeti.cpp)
|
||||
elseif(TELEMETRY STREQUAL FRSKY_SPORT)
|
||||
add_definitions(-DTELEMETRY_FRSKY_SPORT)
|
||||
set(SRC ${SRC} crc16.cpp telemetry/frsky_sport.cpp)
|
||||
|
||||
@@ -95,7 +95,7 @@ uint32_t firmwareWritten = 0;
|
||||
uint32_t eepromAddress = 0;
|
||||
uint32_t eepromWritten = 0;
|
||||
|
||||
TCHAR backupFilename[60];
|
||||
TCHAR backupFilename[_MAX_LFN+1];
|
||||
|
||||
uint32_t Master_frequency;
|
||||
volatile uint8_t Tenms;
|
||||
@@ -229,7 +229,7 @@ const char *getBinaryPath()
|
||||
|
||||
FRESULT openBinaryFile(uint32_t index)
|
||||
{
|
||||
TCHAR filename[60];
|
||||
TCHAR filename[_MAX_LFN+1];
|
||||
FRESULT fr;
|
||||
memset(Block_buffer, 0, sizeof(Block_buffer));
|
||||
strAppend(strAppend(strAppend(filename, getBinaryPath()), "/"), Filenames[index]);
|
||||
@@ -641,4 +641,3 @@ int main()
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
@@ -259,10 +259,7 @@ void frskySportSetDefault(int index, uint16_t id, uint8_t subId, uint8_t instanc
|
||||
TelemetryUnit unit = sensor->unit;
|
||||
uint8_t prec = min<uint8_t>(2, sensor->prec);
|
||||
telemetrySensor.init(sensor->name, unit, prec);
|
||||
if (id == RSSI_ID) {
|
||||
telemetrySensor.logs = true;
|
||||
}
|
||||
else if (id >= ADC1_ID && id <= BATT_ID) {
|
||||
if (id >= ADC1_ID && id <= BATT_ID) {
|
||||
telemetrySensor.custom.ratio = 132;
|
||||
telemetrySensor.filter = 1;
|
||||
}
|
||||
|
||||
@@ -320,19 +320,12 @@ void telemetryReset()
|
||||
telemetryData.hub.gpsFix = -1;
|
||||
#endif
|
||||
|
||||
#if defined(SIMU)
|
||||
|
||||
#if defined(CPUARM)
|
||||
telemetryData.swr.value = 30;
|
||||
telemetryData.rssi.value = 75;
|
||||
#else
|
||||
#if defined(SIMU) && !defined(CPUARM)
|
||||
telemetryData.rssi[0].value = 75;
|
||||
telemetryData.rssi[1].value = 75;
|
||||
telemetryData.analog[TELEM_ANA_A1].set(120, UNIT_VOLTS);
|
||||
telemetryData.analog[TELEM_ANA_A2].set(240, UNIT_VOLTS);
|
||||
#endif
|
||||
|
||||
#if !defined(CPUARM)
|
||||
telemetryData.hub.fuelLevel = 75;
|
||||
telemetryData.hub.rpm = 12000;
|
||||
telemetryData.hub.vfas = 100;
|
||||
@@ -381,32 +374,6 @@ void telemetryReset()
|
||||
telemetryData.hub.current = 55;
|
||||
telemetryData.hub.maxCurrent = 65;
|
||||
#endif
|
||||
#endif
|
||||
|
||||
/*Add some default sensor values to the simulator*/
|
||||
#if defined(CPUARM) && defined(SIMU)
|
||||
for (int i=0; i<MAX_TELEMETRY_SENSORS; i++) {
|
||||
const TelemetrySensor & sensor = g_model.telemetrySensors[i];
|
||||
switch (sensor.id)
|
||||
{
|
||||
case RSSI_ID:
|
||||
setTelemetryValue(TELEM_PROTO_FRSKY_SPORT, RSSI_ID, 0, sensor.instance , 75, UNIT_RAW, 0);
|
||||
break;
|
||||
case ADC1_ID:
|
||||
setTelemetryValue(TELEM_PROTO_FRSKY_SPORT, ADC1_ID, 0, sensor.instance, 100, UNIT_RAW, 0);
|
||||
break;
|
||||
case ADC2_ID:
|
||||
setTelemetryValue(TELEM_PROTO_FRSKY_SPORT, ADC2_ID, 0, sensor.instance, 245, UNIT_RAW, 0);
|
||||
break;
|
||||
case SWR_ID:
|
||||
setTelemetryValue(TELEM_PROTO_FRSKY_SPORT, SWR_ID, 0, sensor.instance, 30, UNIT_RAW, 0);
|
||||
break;
|
||||
case BATT_ID:
|
||||
setTelemetryValue(TELEM_PROTO_FRSKY_SPORT, BATT_ID, 0, sensor.instance, 100, UNIT_RAW, 0);
|
||||
break;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
#if defined(CPUARM)
|
||||
|
||||
@@ -491,6 +491,8 @@ void TelemetrySensor::init(const char * label, uint8_t unit, uint8_t prec)
|
||||
prec = 1;
|
||||
}
|
||||
this->prec = prec;
|
||||
// Log sensors by default
|
||||
this->logs = true;
|
||||
}
|
||||
|
||||
void TelemetrySensor::init(uint16_t id)
|
||||
|
||||
@@ -481,9 +481,9 @@
|
||||
#endif
|
||||
|
||||
#if defined(CPUARM)
|
||||
#define TR_LOGICALSW "L1\0""L2\0""L3\0""L4\0""L5\0""L6\0""L7\0""L8\0""L9\0""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 "L1\0""L2\0""L3\0""L4\0""L5\0""L6\0""L7\0""L8\0""L9\0""L10""L11""L12"
|
||||
#define TR_LOGICALSW "L01""L02""L03""L04""L05""L06""L07""L08""L09""L10""L11""L12"
|
||||
#endif
|
||||
|
||||
#if defined(PCBHORUS)
|
||||
|
||||
@@ -504,9 +504,9 @@
|
||||
#endif
|
||||
|
||||
#if defined(CPUARM)
|
||||
#define TR_LOGICALSW "L1\0""L2\0""L3\0""L4\0""L5\0""L6\0""L7\0""L8\0""L9\0""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 "L1\0""L2\0""L3\0""L4\0""L5\0""L6\0""L7\0""L8\0""L9\0""L10""L11""L12"
|
||||
#define TR_LOGICALSW "L01""L02""L03""L04""L05""L06""L07""L08""L09""L10""L11""L12"
|
||||
#endif
|
||||
|
||||
#if defined(PCBHORUS)
|
||||
|
||||
@@ -487,9 +487,9 @@
|
||||
#endif
|
||||
|
||||
#if defined(CPUARM)
|
||||
#define TR_LOGICALSW "L1\0""L2\0""L3\0""L4\0""L5\0""L6\0""L7\0""L8\0""L9\0""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 "L1\0""L2\0""L3\0""L4\0""L5\0""L6\0""L7\0""L8\0""L9\0""L10""L11""L12"
|
||||
#define TR_LOGICALSW "L01""L02""L03""L04""L05""L06""L07""L08""L09""L10""L11""L12"
|
||||
#endif
|
||||
|
||||
#if defined(PCBHORUS)
|
||||
|
||||
@@ -477,9 +477,9 @@
|
||||
#endif
|
||||
|
||||
#if defined(CPUARM)
|
||||
#define TR_LOGICALSW "L1\0""L2\0""L3\0""L4\0""L5\0""L6\0""L7\0""L8\0""L9\0""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 "L1\0""L2\0""L3\0""L4\0""L5\0""L6\0""L7\0""L8\0""L9\0""L10""L11""L12"
|
||||
#define TR_LOGICALSW "L01""L02""L03""L04""L05""L06""L07""L08""L09""L10""L11""L12"
|
||||
#endif
|
||||
|
||||
#if defined(PCBHORUS)
|
||||
|
||||
@@ -481,9 +481,9 @@
|
||||
#endif
|
||||
|
||||
#if defined(CPUARM)
|
||||
#define TR_LOGICALSW "L1\0""L2\0""L3\0""L4\0""L5\0""L6\0""L7\0""L8\0""L9\0""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 "L1\0""L2\0""L3\0""L4\0""L5\0""L6\0""L7\0""L8\0""L9\0""L10""L11""L12"
|
||||
#define TR_LOGICALSW "L01""L02""L03""L04""L05""L06""L07""L08""L09""L10""L11""L12"
|
||||
#endif
|
||||
|
||||
#if defined(PCBHORUS)
|
||||
|
||||
@@ -494,9 +494,9 @@
|
||||
#endif
|
||||
|
||||
#if defined(CPUARM)
|
||||
#define TR_LOGICALSW "L1\0""L2\0""L3\0""L4\0""L5\0""L6\0""L7\0""L8\0""L9\0""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 "L1\0""L2\0""L3\0""L4\0""L5\0""L6\0""L7\0""L8\0""L9\0""L10""L11""L12"
|
||||
#define TR_LOGICALSW "L01""L02""L03""L04""L05""L06""L07""L08""L09""L10""L11""L12"
|
||||
#endif
|
||||
|
||||
#if defined(PCBHORUS)
|
||||
|
||||
@@ -488,9 +488,9 @@
|
||||
#endif
|
||||
|
||||
#if defined(CPUARM)
|
||||
#define TR_LOGICALSW "L1\0""L2\0""L3\0""L4\0""L5\0""L6\0""L7\0""L8\0""L9\0""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 "L1\0""L2\0""L3\0""L4\0""L5\0""L6\0""L7\0""L8\0""L9\0""L10""L11""L12"
|
||||
#define TR_LOGICALSW "L01""L02""L03""L04""L05""L06""L07""L08""L09""L10""L11""L12"
|
||||
#endif
|
||||
|
||||
#if defined(PCBHORUS)
|
||||
|
||||
@@ -478,9 +478,9 @@
|
||||
#endif
|
||||
|
||||
#if defined(CPUARM)
|
||||
#define TR_LOGICALSW "L1\0""L2\0""L3\0""L4\0""L5\0""L6\0""L7\0""L8\0""L9\0""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 "L1\0""L2\0""L3\0""L4\0""L5\0""L6\0""L7\0""L8\0""L9\0""L10""L11""L12"
|
||||
#define TR_LOGICALSW "L01""L02""L03""L04""L05""L06""L07""L08""L09""L10""L11""L12"
|
||||
#endif
|
||||
|
||||
#if defined(PCBHORUS)
|
||||
|
||||
@@ -490,9 +490,9 @@
|
||||
#endif
|
||||
|
||||
#if defined(CPUARM)
|
||||
#define TR_LOGICALSW "L1\0""L2\0""L3\0""L4\0""L5\0""L6\0""L7\0""L8\0""L9\0""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 "L1\0""L2\0""L3\0""L4\0""L5\0""L6\0""L7\0""L8\0""L9\0""L10""L11""L12"
|
||||
#define TR_LOGICALSW "L01""L02""L03""L04""L05""L06""L07""L08""L09""L10""L11""L12"
|
||||
#endif
|
||||
|
||||
#if defined(PCBHORUS)
|
||||
|
||||
@@ -478,9 +478,9 @@
|
||||
#endif
|
||||
|
||||
#if defined(CPUARM)
|
||||
#define TR_LOGICALSW "L1\0""L2\0""L3\0""L4\0""L5\0""L6\0""L7\0""L8\0""L9\0""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 "L1\0""L2\0""L3\0""L4\0""L5\0""L6\0""L7\0""L8\0""L9\0""L10""L11""L12"
|
||||
#define TR_LOGICALSW "L01""L02""L03""L04""L05""L06""L07""L08""L09""L10""L11""L12"
|
||||
#endif
|
||||
|
||||
#if defined(PCBHORUS)
|
||||
|
||||
@@ -495,9 +495,9 @@
|
||||
#endif
|
||||
|
||||
#if defined(CPUARM)
|
||||
#define TR_LOGICALSW "L1\0""L2\0""L3\0""L4\0""L5\0""L6\0""L7\0""L8\0""L9\0""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 "L1\0""L2\0""L3\0""L4\0""L5\0""L6\0""L7\0""L8\0""L9\0""L10""L11""L12"
|
||||
#define TR_LOGICALSW "L01""L02""L03""L04""L05""L06""L07""L08""L09""L10""L11""L12"
|
||||
#endif
|
||||
|
||||
#if defined(PCBHORUS)
|
||||
|
||||
@@ -179,63 +179,32 @@ I18N_PLAY_FUNCTION(it, playNumber, getvalue_t number, uint8_t unit, uint8_t att)
|
||||
|
||||
I18N_PLAY_FUNCTION(it, playDuration, int seconds PLAY_DURATION_ATT)
|
||||
{
|
||||
if (seconds == 0) {
|
||||
PLAY_NUMBER(seconds, 0, 0);
|
||||
return;
|
||||
}
|
||||
|
||||
if (seconds < 0) {
|
||||
PUSH_NUMBER_PROMPT(IT_PROMPT_MENO);
|
||||
seconds = -seconds;
|
||||
}
|
||||
|
||||
uint8_t ore = 0;
|
||||
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) {
|
||||
ore=tmp;
|
||||
if (tmp > 1 || IS_PLAY_TIME()) {
|
||||
#if defined(CPUARM)
|
||||
PLAY_NUMBER(tmp, UNIT_HOURS, 0);
|
||||
#else
|
||||
PLAY_NUMBER(tmp, 0, 0);
|
||||
PUSH_NUMBER_PROMPT(IT_PROMPT_ORE);
|
||||
} else {
|
||||
PUSH_NUMBER_PROMPT(IT_PROMPT_UN);
|
||||
PUSH_NUMBER_PROMPT(IT_PROMPT_ORA);
|
||||
#endif
|
||||
}
|
||||
}
|
||||
if (seconds>0) {
|
||||
tmp = seconds / 60;
|
||||
seconds %= 60;
|
||||
if (tmp>0 && seconds==0 && ore>0) {
|
||||
PLAY_NUMBER(tmp, UNIT_MINUTES, 0);
|
||||
if (seconds > 0)
|
||||
PUSH_NUMBER_PROMPT(IT_PROMPT_E);
|
||||
}
|
||||
if (tmp > 0) {
|
||||
if (tmp != 1) {
|
||||
#if defined(CPUARM)
|
||||
PLAY_NUMBER(tmp, UNIT_MINUTES, 0);
|
||||
#else
|
||||
PLAY_NUMBER(tmp, 0, 0);
|
||||
PUSH_NUMBER_PROMPT(IT_PROMPT_MINUTI);
|
||||
} else {
|
||||
PUSH_NUMBER_PROMPT(IT_PROMPT_UN);
|
||||
PUSH_NUMBER_PROMPT(IT_PROMPT_MINUTO);
|
||||
#endif
|
||||
}
|
||||
}
|
||||
if ((tmp>0 || ore>0) && seconds>0) {
|
||||
PUSH_NUMBER_PROMPT(IT_PROMPT_E);
|
||||
}
|
||||
}
|
||||
if (seconds != 0 || (ore==0 && tmp==0)) {
|
||||
if (seconds != 1) {
|
||||
#if defined(CPUARM)
|
||||
PLAY_NUMBER(tmp, UNIT_SECONDS, 0);
|
||||
#else
|
||||
PLAY_NUMBER(seconds, 0, 0);
|
||||
PUSH_NUMBER_PROMPT(IT_PROMPT_SECONDI);
|
||||
} else {
|
||||
PUSH_NUMBER_PROMPT(IT_PROMPT_UN);
|
||||
PUSH_NUMBER_PROMPT(IT_PROMPT_SECONDO);
|
||||
#endif
|
||||
}
|
||||
|
||||
if (seconds > 0) {
|
||||
PLAY_NUMBER(seconds, UNIT_SECONDS, 0);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
+92
-92
@@ -12,103 +12,103 @@ for i, s in enumerate(["nula", "jedna", "dva"]):
|
||||
systemSounds.append((s, filename(PROMPT_SYSTEM_BASE + i)))
|
||||
for i in range(97):
|
||||
systemSounds.append((str(3 + i), filename(PROMPT_SYSTEM_BASE + 3 + i)))
|
||||
for i, s in enumerate(["sto", u"dvěsta", u"třista", u"čtyřista", u"pětset", u"šestset", "sedmset", "osmset",
|
||||
u"devětset", u"tisíc"]):
|
||||
for i, s in enumerate(["sto", "dvěsta", "třista", "čtyřista", "pětset", "šestset", "sedmset", "osmset",
|
||||
"devětset", "tisíc"]):
|
||||
systemSounds.append((s, filename(PROMPT_SYSTEM_BASE + 100 + i)))
|
||||
for i, s in enumerate([u"tisíce", "jeden", "jedno", u"dvě", u"celá", u"celé", u"celých", u"mínus"]):
|
||||
for i, s in enumerate(["tisíce", "jeden", "jedno", "dvě", "celá", "celé", "celých", "mínus"]):
|
||||
systemSounds.append((s, filename(PROMPT_SYSTEM_BASE + 110 + i)))
|
||||
for i, (s, f) in enumerate([(u"volt", u"volt0"), (u"volty", u"volt1"), (u"voltů", u"volt2"),(u"voltu", u"volt3"),
|
||||
(u"ampér", "amp0"), (u"ampéry", u"amp1"), (u"ampérů", u"amp2"), (u"ampéru", u"amp3"),
|
||||
(u"miliampér", "mamp0"), (u"miliampéry", u"mamp1"), (u"miliampérů", u"mamp2"), (u"miliampéru", u"mamp3"),
|
||||
(u"uzel", "knot0"), (u"uzly", u"knot1"), (u"uzlů", u"knot2"), (u"uzlu", u"knot3"),
|
||||
(u"metr za sekundu", "mps0"), (u"metry za sekundu", u"mps1"), (u"metrů za sekundu", u"mps2"), (u"metru za sekundu", u"mps3"),
|
||||
(u"stopa za sekundu", "fps0"), (u"stopy za sekundu", u"fps1"), (u"stop za sekundu", u"fps2"), (u"stopy za sekundu", u"fps3"),
|
||||
(u"kilometr za hodinu", "kph0"), (u"kilometry za hodinu", u"kph1"), (u"kilometrů za hodinu", u"kph2"), (u"kilometru za hodinu", u"kph3"),
|
||||
(u"míle za hodinu", "mph0"), (u"míle za hodinu", u"mph1"), (u"mil za hodinu", u"mph2"), (u"míle za hodinu", u"mph3"),
|
||||
(u"metr", "meter0"), (u"metry", u"meter1"), (u"metrů", u"meter2"), (u"metru", u"meter3"),
|
||||
(u"stopa", "foot0"), (u"stopy", u"foot1"), (u"stop", u"foot2"),(u"stopy", u"foot3"),
|
||||
(u"stupeň celsia", "celsius0"), (u"stupně celsia", u"celsius1"), (u"stupňů celsia", u"celsius2"), (u"stupně celsia", u"celsius3"),
|
||||
(u"stupeň fahrenheita", "fahr0"), (u"stupně fahrenheita", u"fahr1"), (u"stupňů fahrenheita", u"fahr2"), (u"stupně fahrenheita", u"fahr3"),
|
||||
(u"procento", "percent0"), (u"procenta", u"percent1"), (u"procent", u"percent2"), (u"procenta", u"percent3"),
|
||||
(u"miliampérhodina", "mamph0"), (u"miliampérhodiny", u"mamph1"), (u"miliampérhodin", u"mamph2"), (u"miliampérhodiny", u"mamph3"),
|
||||
(u"vat", "watt0"), (u"vaty", u"watt1"), (u"vatů", u"watt2"), (u"vatu", u"watt3"),
|
||||
(u"milivat", "mwatt0"), (u"milivaty", u"mwatt1"), (u"milivatů", u"mwatt2"), (u"milivatu", u"mwatt3"),
|
||||
(u"decibel", "db0"), (u"decibely", u"db1"), (u"decibelů", u"db2"), (u"decibelu", u"db3"),
|
||||
(u"otáčka za minutu", "rpm0"), (u"otáčky za minutu", u"rpm1"), (u"otáček za minutu", u"rpm2"), (u"otáčky za minutu", u"rpm3"),
|
||||
(u"gé", "g0"), (u"gé", "g1"), (u"gé", "g2"), (u"gé", "g3"),
|
||||
(u"stupeň", "degree0"), (u"stupně", u"degree1"), (u"stupňů", u"degree2"), (u"stupně", u"degree3"),
|
||||
(u"radián", "rad0"), (u"radiány", "rad1"), (u"radiánů", "rad2"), (u"radiánu", "rad3"),
|
||||
(u"mililitr", "ml0"), (u"mililitry", u"ml1"), (u"mililitrů", u"ml2"), (u"mililitru", u"ml3"),
|
||||
(u"dutá unce", "founce0"), (u"duté unce", u"founce1"), (u"dutých uncí", u"founce2"), (u"duté unce", u"founce3"),
|
||||
(u"hodina", "hour0"), (u"hodiny", u"hour1"), (u"hodin", u"hour2"), (u"hodiny", u"hour3"),
|
||||
(u"minuta", "minute0"), (u"minuty", u"minute1"), (u"minut", u"minute2"), (u"minuty", u"minute3"),
|
||||
(u"sekunda", "second0"), (u"sekundy", u"second1"), (u"sekund", u"second2"), (u"sekundy", u"second3"),
|
||||
for i, (s, f) in enumerate([("volt", "volt0"), ("volty", "volt1"), ("voltů", "volt2"),("voltu", "volt3"),
|
||||
("ampér", "amp0"), ("ampéry", "amp1"), ("ampérů", "amp2"), ("ampéru", "amp3"),
|
||||
("miliampér", "mamp0"), ("miliampéry", "mamp1"), ("miliampérů", "mamp2"), ("miliampéru", "mamp3"),
|
||||
("uzel", "knot0"), ("uzly", "knot1"), ("uzlů", "knot2"), ("uzlu", "knot3"),
|
||||
("metr za sekundu", "mps0"), ("metry za sekundu", "mps1"), ("metrů za sekundu", "mps2"), ("metru za sekundu", "mps3"),
|
||||
("stopa za sekundu", "fps0"), ("stopy za sekundu", "fps1"), ("stop za sekundu", "fps2"), ("stopy za sekundu", "fps3"),
|
||||
("kilometr za hodinu", "kph0"), ("kilometry za hodinu", "kph1"), ("kilometrů za hodinu", "kph2"), ("kilometru za hodinu", "kph3"),
|
||||
("míle za hodinu", "mph0"), ("míle za hodinu", "mph1"), ("mil za hodinu", "mph2"), ("míle za hodinu", "mph3"),
|
||||
("metr", "meter0"), ("metry", "meter1"), ("metrů", "meter2"), ("metru", "meter3"),
|
||||
("stopa", "foot0"), ("stopy", "foot1"), ("stop", "foot2"),("stopy", "foot3"),
|
||||
("stupeň celsia", "celsius0"), ("stupně celsia", "celsius1"), ("stupňů celsia", "celsius2"), ("stupně celsia", "celsius3"),
|
||||
("stupeň fahrenheita", "fahr0"), ("stupně fahrenheita", "fahr1"), ("stupňů fahrenheita", "fahr2"), ("stupně fahrenheita", "fahr3"),
|
||||
("procento", "percent0"), ("procenta", "percent1"), ("procent", "percent2"), ("procenta", "percent3"),
|
||||
("miliampérhodina", "mamph0"), ("miliampérhodiny", "mamph1"), ("miliampérhodin", "mamph2"), ("miliampérhodiny", "mamph3"),
|
||||
("vat", "watt0"), ("vaty", "watt1"), ("vatů", "watt2"), ("vatu", "watt3"),
|
||||
("milivat", "mwatt0"), ("milivaty", "mwatt1"), ("milivatů", "mwatt2"), ("milivatu", "mwatt3"),
|
||||
("decibel", "db0"), ("decibely", "db1"), ("decibelů", "db2"), ("decibelu", "db3"),
|
||||
("otáčka za minutu", "rpm0"), ("otáčky za minutu", "rpm1"), ("otáček za minutu", "rpm2"), ("otáčky za minutu", "rpm3"),
|
||||
("gé", "g0"), ("gé", "g1"), ("gé", "g2"), ("gé", "g3"),
|
||||
("stupeň", "degree0"), ("stupně", "degree1"), ("stupňů", "degree2"), ("stupně", "degree3"),
|
||||
("radián", "rad0"), ("radiány", "rad1"), ("radiánů", "rad2"), ("radiánu", "rad3"),
|
||||
("mililitr", "ml0"), ("mililitry", "ml1"), ("mililitrů", "ml2"), ("mililitru", "ml3"),
|
||||
("dutá unce", "founce0"), ("duté unce", "founce1"), ("dutých uncí", "founce2"), ("duté unce", "founce3"),
|
||||
("hodina", "hour0"), ("hodiny", "hour1"), ("hodin", "hour2"), ("hodiny", "hour3"),
|
||||
("minuta", "minute0"), ("minuty", "minute1"), ("minut", "minute2"), ("minuty", "minute3"),
|
||||
("sekunda", "second0"), ("sekundy", "second1"), ("sekund", "second2"), ("sekundy", "second3"),
|
||||
]):
|
||||
systemSounds.append((s, filename(f, PROMPT_SYSTEM_BASE + 118 + i)))
|
||||
for s, f, a in [(u"střed trimu", "midtrim", 495),
|
||||
(u"maximum trimu", "maxtrim", NO_ALTERNATE),
|
||||
(u"minimum trimu", "mintrim", NO_ALTERNATE),
|
||||
(u"stopky 1 doběhly", "timovr1", NO_ALTERNATE),
|
||||
(u"stopky 2 doběhly", "timovr2", NO_ALTERNATE),
|
||||
(u"stopky 3 doběhly", "timovr3", NO_ALTERNATE),
|
||||
(u"baterie rádia je vybitá", "lowbatt", 485),
|
||||
(u"zapoměl jsi na mě!", "inactiv", 486),
|
||||
(u"plyn není na nule", "thralert", 481),
|
||||
(u"přepínače nejsou ve výchozí poloze", "swalert", 482),
|
||||
(u"neplatná eeprom", "eebad", 483),
|
||||
(u"Oupn najn iks", "hello", 480),
|
||||
(u"Tak zase příště!", "bye", 480),
|
||||
(u"dvacet sekund", "timer20", 500),
|
||||
(u"třicet sekund", "timer30", 501),
|
||||
(u"A1,nízká", "a1_org", NO_ALTERNATE),
|
||||
(u"A1,kritická", "a1_red", NO_ALTERNATE),
|
||||
(u"A2,nízká", "a2_org", NO_ALTERNATE),
|
||||
(u"A2,kritická", "a2_red", NO_ALTERNATE),
|
||||
(u"A3,nízká", "a3_org", NO_ALTERNATE),
|
||||
(u"A3,kritická", "a3_red", NO_ALTERNATE),
|
||||
(u"A4,nízká", "a4_org", NO_ALTERNATE),
|
||||
(u"A4,kritická", "a4_red", NO_ALTERNATE),
|
||||
(u"nízký RF signál", "rssi_org", NO_ALTERNATE),
|
||||
(u"kritický RF signál", "rssi_red", NO_ALTERNATE),
|
||||
(u"problém s anténou rádia", "swr_red", NO_ALTERNATE),
|
||||
(u"telemetrie ztracena", "telemko", NO_ALTERNATE),
|
||||
(u"telemetrie je funkční", "telemok", NO_ALTERNATE),
|
||||
(u"trenér port odpojen", "trainko", NO_ALTERNATE),
|
||||
(u"trenér port připojen", "trainok", NO_ALTERNATE),
|
||||
(u"senzor ztracen", "sensorko", NO_ALTERNATE),
|
||||
(u"servo přetíženo", "servoko", NO_ALTERNATE),
|
||||
(u"r f přebuzeno", "rxko", NO_ALTERNATE),
|
||||
for s, f, a in [("střed trimu", "midtrim", 495),
|
||||
("maximum trimu", "maxtrim", NO_ALTERNATE),
|
||||
("minimum trimu", "mintrim", NO_ALTERNATE),
|
||||
("stopky 1 doběhly", "timovr1", NO_ALTERNATE),
|
||||
("stopky 2 doběhly", "timovr2", NO_ALTERNATE),
|
||||
("stopky 3 doběhly", "timovr3", NO_ALTERNATE),
|
||||
("baterie rádia je vybitá", "lowbatt", 485),
|
||||
("zapoměl jsi na mě!", "inactiv", 486),
|
||||
("plyn není na nule", "thralert", 481),
|
||||
("přepínače nejsou ve výchozí poloze", "swalert", 482),
|
||||
("neplatná eeprom", "eebad", 483),
|
||||
("Oupn najn iks", "hello", 480),
|
||||
("Tak zase příště!", "bye", 480),
|
||||
("dvacet sekund", "timer20", 500),
|
||||
("třicet sekund", "timer30", 501),
|
||||
("A1,nízká", "a1_org", NO_ALTERNATE),
|
||||
("A1,kritická", "a1_red", NO_ALTERNATE),
|
||||
("A2,nízká", "a2_org", NO_ALTERNATE),
|
||||
("A2,kritická", "a2_red", NO_ALTERNATE),
|
||||
("A3,nízká", "a3_org", NO_ALTERNATE),
|
||||
("A3,kritická", "a3_red", NO_ALTERNATE),
|
||||
("A4,nízká", "a4_org", NO_ALTERNATE),
|
||||
("A4,kritická", "a4_red", NO_ALTERNATE),
|
||||
("nízký RF signál", "rssi_org", NO_ALTERNATE),
|
||||
("kritický RF signál", "rssi_red", NO_ALTERNATE),
|
||||
("problém s anténou rádia", "swr_red", NO_ALTERNATE),
|
||||
("telemetrie ztracena", "telemko", NO_ALTERNATE),
|
||||
("telemetrie je funkční", "telemok", NO_ALTERNATE),
|
||||
("trenér port odpojen", "trainko", NO_ALTERNATE),
|
||||
("trenér port připojen", "trainok", NO_ALTERNATE),
|
||||
("senzor ztracen", "sensorko", NO_ALTERNATE),
|
||||
("servo přetíženo", "servoko", NO_ALTERNATE),
|
||||
("r f přebuzeno", "rxko", NO_ALTERNATE),
|
||||
]:
|
||||
systemSounds.append((s, filename(f, a)))
|
||||
for i, (s, f) in enumerate([(u"podvozek je zasunut", "podvo0"),
|
||||
(u"podvozek je vysunut", "podvo1"),
|
||||
(u"klapky jsou zapnuty", "klapk1"),
|
||||
(u"klapky jsou vypnuty", "klapk0"),
|
||||
(u"trenér je zapnut", "trene1"),
|
||||
(u"trenér je vypnutý", "trene0"),
|
||||
(u"motor je vypnut", "motor0"),
|
||||
(u"motor je aktivován", "motor1"),
|
||||
(u"jsi příliš vysoko", "vysoko"),
|
||||
(u"jsi příliš nízko", "nizko"),
|
||||
(u"baterie modelu je vybitá", "bat0"),
|
||||
(u"dochází palivo", "palivo"),
|
||||
(u"nízký signál!", "nsigna"),
|
||||
(u"kritický signál!", "ksigna"),
|
||||
(u"rychlý režim aktivován", "rrychl"),
|
||||
(u"termický režim aktivován", "rtermi"),
|
||||
(u"normální režim aktivován", "rnorm"),
|
||||
(u"režim start aktivován", "rstart"),
|
||||
(u"režim přistání aktivován", "prista"),
|
||||
(u"vario je zapnuto", "vario0"),
|
||||
(u"vario je vypnuto", "vario1"),
|
||||
(u"start povolen", "start1"),
|
||||
(u"letový režim jedna", "fm-1"),
|
||||
(u"letový režim dva", "fm-2"),
|
||||
(u"letový režim tři", "fm-3"),
|
||||
(u"letový režim čtyři", "fm-4"),
|
||||
(u"letový režim pět", "fm-5"),
|
||||
(u"letový režim šest", "fm-6"),
|
||||
(u"letový režim sedm", "fm-7"),
|
||||
(u"letový režim osm", "fm-8"),
|
||||
for i, (s, f) in enumerate([("podvozek je zasunut", "podvo0"),
|
||||
("podvozek je vysunut", "podvo1"),
|
||||
("klapky jsou zapnuty", "klapk1"),
|
||||
("klapky jsou vypnuty", "klapk0"),
|
||||
("trenér je zapnut", "trene1"),
|
||||
("trenér je vypnutý", "trene0"),
|
||||
("motor je vypnut", "motor0"),
|
||||
("motor je aktivován", "motor1"),
|
||||
("jsi příliš vysoko", "vysoko"),
|
||||
("jsi příliš nízko", "nizko"),
|
||||
("baterie modelu je vybitá", "bat0"),
|
||||
("dochází palivo", "palivo"),
|
||||
("nízký signál!", "nsigna"),
|
||||
("kritický signál!", "ksigna"),
|
||||
("rychlý režim aktivován", "rrychl"),
|
||||
("termický režim aktivován", "rtermi"),
|
||||
("normální režim aktivován", "rnorm"),
|
||||
("režim start aktivován", "rstart"),
|
||||
("režim přistání aktivován", "prista"),
|
||||
("vario je zapnuto", "vario0"),
|
||||
("vario je vypnuto", "vario1"),
|
||||
("start povolen", "start1"),
|
||||
("letový režim jedna", "fm-1"),
|
||||
("letový režim dva", "fm-2"),
|
||||
("letový režim tři", "fm-3"),
|
||||
("letový režim čtyři", "fm-4"),
|
||||
("letový režim pět", "fm-5"),
|
||||
("letový režim šest", "fm-6"),
|
||||
("letový režim sedm", "fm-7"),
|
||||
("letový režim osm", "fm-8"),
|
||||
]):
|
||||
sounds.append((s, filename(f, PROMPT_CUSTOM_BASE + i)))
|
||||
|
||||
+82
-82
@@ -16,64 +16,64 @@ systemSounds.append(("hundert", filename(PROMPT_SYSTEM_BASE + 102)))
|
||||
systemSounds.append(("tausend", filename(PROMPT_SYSTEM_BASE + 103)))
|
||||
for i, s in enumerate(["komma", "und", "minus", "uhr", "minute", "minuten", "sekunde", "sekunden", "stunde", "stunden"]):
|
||||
systemSounds.append((s, filename(PROMPT_SYSTEM_BASE + 104 + i)))
|
||||
for i, (s, f) in enumerate([(u"Wolt","volt0"),
|
||||
(u"Ampär", "amp0"),
|
||||
(u"MilliAmpär", "mamp0"),
|
||||
(u"Knoten", "knot0"),
|
||||
(u"Meter pro sekunde", "mps0"),
|
||||
(u"Fuss pro sekunde", "fps0"),
|
||||
(u"Kilometer pro stunde", "kph0"),
|
||||
(u"Meilen pro Stunde", "mph0"),
|
||||
(u"Meter", "meter0"),
|
||||
(u"Fuesse", "foot0"),
|
||||
(u"Grad Celsius", "celsius0"),
|
||||
(u"Grad Fahrenheit", "fahr0"),
|
||||
(u"Prozent", "percent0"),
|
||||
(u"Milliampär pro stunde", "mamph0"),
|
||||
(u"Watt", "watt0"),
|
||||
(u"Milli Watt", "mwatt0"),
|
||||
(u"D B", "db0"),
|
||||
(u"Drehzahl", "rpm0"),
|
||||
(u"g", "g0"),
|
||||
(u"Grad", "degree0"),
|
||||
(u"radians", "rad0"),
|
||||
(u"Milliliter", "ml0"),
|
||||
(u"Unze", "founce0"),
|
||||
(u"Stunde", "hour0"), (u"Stunden", "hour1"),
|
||||
(u"Minute", "minute0"), (u"Minuten", "minute1"),
|
||||
(u"Sekunde", "second0"), (u"Sekunden", "second1"),
|
||||
for i, (s, f) in enumerate([("Wolt","volt0"),
|
||||
("Ampär", "amp0"),
|
||||
("MilliAmpär", "mamp0"),
|
||||
("Knoten", "knot0"),
|
||||
("Meter pro sekunde", "mps0"),
|
||||
("Fuss pro sekunde", "fps0"),
|
||||
("Kilometer pro stunde", "kph0"),
|
||||
("Meilen pro Stunde", "mph0"),
|
||||
("Meter", "meter0"),
|
||||
("Fuesse", "foot0"),
|
||||
("Grad Celsius", "celsius0"),
|
||||
("Grad Fahrenheit", "fahr0"),
|
||||
("Prozent", "percent0"),
|
||||
("Milliampär pro stunde", "mamph0"),
|
||||
("Watt", "watt0"),
|
||||
("Milli Watt", "mwatt0"),
|
||||
("D B", "db0"),
|
||||
("Drehzahl", "rpm0"),
|
||||
("g", "g0"),
|
||||
("Grad", "degree0"),
|
||||
("radians", "rad0"),
|
||||
("Milliliter", "ml0"),
|
||||
("Unze", "founce0"),
|
||||
("Stunde", "hour0"), ("Stunden", "hour1"),
|
||||
("Minute", "minute0"), ("Minuten", "minute1"),
|
||||
("Sekunde", "second0"), ("Sekunden", "second1"),
|
||||
]):
|
||||
systemSounds.append((s, filename(f, PROMPT_SYSTEM_BASE + 114 + i)))
|
||||
for s, f, a in [(u"Inaktivitätsalarm", "inactiv", 486),
|
||||
(u"Senderspannung schwach", "lowbatt", 485),
|
||||
(u"Gaskanal nicht Null, bitte prüfen", "thralert", 481),
|
||||
(u"Schalter fehlpositioniert, bitte prüfen", "swalert", 482),
|
||||
(u"EEPROM fehlerhaft", "eebad", NO_ALTERNATE),
|
||||
(u"EEPROM formatiert", "eeformat", NO_ALTERNATE),
|
||||
(u"Fehler", "error", NO_ALTERNATE),
|
||||
(u"Trim zentriert", "midtrim", 495),
|
||||
(u"Poti zentriert", "midpot", 496),
|
||||
(u"Obere Trimmungsgrenze erreicht", "maxtrim", NO_ALTERNATE),
|
||||
(u"Untere Trimmungsgrenze erreicht", "mintrim", NO_ALTERNATE),
|
||||
(u"20 Sekunden", "timer20", 500),
|
||||
(u"30 Sekunden", "timer30", 501),
|
||||
(u"Senderstrom zu hoch!", "highmah", NO_ALTERNATE),
|
||||
(u"Sendertemperatur zu hoch!", "hightemp", NO_ALTERNATE),
|
||||
(u"A1 schwach!", "a1_org", NO_ALTERNATE),
|
||||
(u"A1 kritisch!", "a1_red", NO_ALTERNATE),
|
||||
(u"A2 schwach!", "a2_org", NO_ALTERNATE),
|
||||
(u"A2 kritisch!", "a2_red", NO_ALTERNATE),
|
||||
(u"A3 schwach!", "a3_org", NO_ALTERNATE),
|
||||
(u"A3 kritisch!", "a3_red", NO_ALTERNATE),
|
||||
(u"A4 schwach!", "a4_org", NO_ALTERNATE),
|
||||
(u"A4 kritisch!", "a4_red", NO_ALTERNATE),
|
||||
(u"Funksignal schwach!", "rssi_org", NO_ALTERNATE),
|
||||
(u"Funksignal kritisch!", "rssi_red", NO_ALTERNATE),
|
||||
(u"Problem mit der Sender Antenne", "swr_red", NO_ALTERNATE),
|
||||
(u"Telemetrie verloren", "telemko", NO_ALTERNATE),
|
||||
(u"Telemetrie wiederhergestellt", "telemok", NO_ALTERNATE),
|
||||
(u"Schülersignal verloren", "trainko", NO_ALTERNATE),
|
||||
(u"Schülersignal wiederhergestellt", "trainok", NO_ALTERNATE),
|
||||
for s, f, a in [("Inaktivitätsalarm", "inactiv", 486),
|
||||
("Senderspannung schwach", "lowbatt", 485),
|
||||
("Gaskanal nicht Null, bitte prüfen", "thralert", 481),
|
||||
("Schalter fehlpositioniert, bitte prüfen", "swalert", 482),
|
||||
("EEPROM fehlerhaft", "eebad", NO_ALTERNATE),
|
||||
("EEPROM formatiert", "eeformat", NO_ALTERNATE),
|
||||
("Fehler", "error", NO_ALTERNATE),
|
||||
("Trim zentriert", "midtrim", 495),
|
||||
("Poti zentriert", "midpot", 496),
|
||||
("Obere Trimmungsgrenze erreicht", "maxtrim", NO_ALTERNATE),
|
||||
("Untere Trimmungsgrenze erreicht", "mintrim", NO_ALTERNATE),
|
||||
("20 Sekunden", "timer20", 500),
|
||||
("30 Sekunden", "timer30", 501),
|
||||
("Senderstrom zu hoch!", "highmah", NO_ALTERNATE),
|
||||
("Sendertemperatur zu hoch!", "hightemp", NO_ALTERNATE),
|
||||
("A1 schwach!", "a1_org", NO_ALTERNATE),
|
||||
("A1 kritisch!", "a1_red", NO_ALTERNATE),
|
||||
("A2 schwach!", "a2_org", NO_ALTERNATE),
|
||||
("A2 kritisch!", "a2_red", NO_ALTERNATE),
|
||||
("A3 schwach!", "a3_org", NO_ALTERNATE),
|
||||
("A3 kritisch!", "a3_red", NO_ALTERNATE),
|
||||
("A4 schwach!", "a4_org", NO_ALTERNATE),
|
||||
("A4 kritisch!", "a4_red", NO_ALTERNATE),
|
||||
("Funksignal schwach!", "rssi_org", NO_ALTERNATE),
|
||||
("Funksignal kritisch!", "rssi_red", NO_ALTERNATE),
|
||||
("Problem mit der Sender Antenne", "swr_red", NO_ALTERNATE),
|
||||
("Telemetrie verloren", "telemko", NO_ALTERNATE),
|
||||
("Telemetrie wiederhergestellt", "telemok", NO_ALTERNATE),
|
||||
("Schülersignal verloren", "trainko", NO_ALTERNATE),
|
||||
("Schülersignal wiederhergestellt", "trainok", NO_ALTERNATE),
|
||||
]:
|
||||
systemSounds.append((s, filename(f, a)))
|
||||
for i, s in enumerate(["Uhr", "Uhr", "Sender", "Empfang", "A1", "A2", "Hoehe", "Motor",
|
||||
@@ -81,31 +81,31 @@ for i, s in enumerate(["Uhr", "Uhr", "Sender", "Empfang", "A1", "A2", "Hoehe", "
|
||||
"Zellen gesamt", "Spannung", "Strom", "Verbrauch", "Power", "Beschleunigung X", "Beschleunigung Y", "Beschleunigung Z",
|
||||
"Richtung", "Variometer", "Minimum", "Maximum"]):
|
||||
systemSounds.append((s, filename(PROMPT_SYSTEM_BASE + 134 + i)))
|
||||
for i, (s, f) in enumerate([(u"Fahrwerk eingezogen", "gearup"),
|
||||
(u"Fahrwerk ausgefahren", "geardn"),
|
||||
(u"Klappen eingefahren", "flapup"),
|
||||
(u"Klappen ausgefahren", "flapdn"),
|
||||
(u"Landung", "lnding"),
|
||||
(u"Trainer-Modus ein", "trnon"),
|
||||
(u"Trainer-Modus aus", "trnoff"),
|
||||
(u"Motor aus", "engoff"),
|
||||
(u"Motor an", "engon"),
|
||||
(u"zu hoch", "tohigh"),
|
||||
(u"zu niedrig", "tolow"),
|
||||
(u"Batterie schwach", "lowbatt"),
|
||||
(u"Butterfly ein", "crowon"),
|
||||
(u"Butterfly aus", "crowof"),
|
||||
(u"Geschwindigkeits-Modus ist aktiviert", "fm-spd"),
|
||||
(u"Thermik-Modus ist aktiviert", "fm-thm"),
|
||||
(u"Normal-Modus ist aktiviert", "fm-nrm"),
|
||||
(u"Flugmodus 1", "fm-1"),
|
||||
(u"Flugmodus 2", "fm-2"),
|
||||
(u"Flugmodus 3", "fm-3"),
|
||||
(u"Flugmodus 4", "fm-4"),
|
||||
(u"Flugmodus 5", "fm-5"),
|
||||
(u"Flugmodus 6", "fm-6"),
|
||||
(u"Flugmodus 7", "fm-7"),
|
||||
(u"Flugmodus 8", "fm-8"),
|
||||
(u"Flugmodus 9", "fm-9"),
|
||||
for i, (s, f) in enumerate([("Fahrwerk eingezogen", "gearup"),
|
||||
("Fahrwerk ausgefahren", "geardn"),
|
||||
("Klappen eingefahren", "flapup"),
|
||||
("Klappen ausgefahren", "flapdn"),
|
||||
("Landung", "lnding"),
|
||||
("Trainer-Modus ein", "trnon"),
|
||||
("Trainer-Modus aus", "trnoff"),
|
||||
("Motor aus", "engoff"),
|
||||
("Motor an", "engon"),
|
||||
("zu hoch", "tohigh"),
|
||||
("zu niedrig", "tolow"),
|
||||
("Batterie schwach", "lowbatt"),
|
||||
("Butterfly ein", "crowon"),
|
||||
("Butterfly aus", "crowof"),
|
||||
("Geschwindigkeits-Modus ist aktiviert", "fm-spd"),
|
||||
("Thermik-Modus ist aktiviert", "fm-thm"),
|
||||
("Normal-Modus ist aktiviert", "fm-nrm"),
|
||||
("Flugmodus 1", "fm-1"),
|
||||
("Flugmodus 2", "fm-2"),
|
||||
("Flugmodus 3", "fm-3"),
|
||||
("Flugmodus 4", "fm-4"),
|
||||
("Flugmodus 5", "fm-5"),
|
||||
("Flugmodus 6", "fm-6"),
|
||||
("Flugmodus 7", "fm-7"),
|
||||
("Flugmodus 8", "fm-8"),
|
||||
("Flugmodus 9", "fm-9"),
|
||||
]):
|
||||
sounds.append((s, filename(f, PROMPT_CUSTOM_BASE + i)))
|
||||
|
||||
+67
-67
@@ -46,74 +46,74 @@ for i, s in enumerate(["point zero", "point one", "point two", "point three",
|
||||
"point four", "point five", "point six",
|
||||
"point seven", "point eight", "point nine"]):
|
||||
systemSounds.append((s, filename(PROMPT_SYSTEM_BASE + 167 + i)))
|
||||
for s, f, a in [(u"trim center", "midtrim", 495),
|
||||
(u"maximum trim reached", "maxtrim", NO_ALTERNATE),
|
||||
(u"minimum trim reached", "mintrim", NO_ALTERNATE),
|
||||
(u"timer 1 elapsed", "timovr1", NO_ALTERNATE),
|
||||
(u"timer 2 elapsed", "timovr2", NO_ALTERNATE),
|
||||
(u"timer 3 elapsed", "timovr3", NO_ALTERNATE),
|
||||
(u"transmitter battery low", "lowbatt", 485),
|
||||
(u"inactivity alarm", "inactiv", 486),
|
||||
(u"throttle warning", "thralert", 481),
|
||||
(u"switch warning", "swalert", 482),
|
||||
(u"bad eeprom", "eebad", 483),
|
||||
(u"Welcome to open tea ex!", "hello", 480),
|
||||
(u"RF signal, low", "rssi_org", NO_ALTERNATE),
|
||||
(u"RF signal, critical", "rssi_red", NO_ALTERNATE),
|
||||
(u"radio antenna defective", "swr_red", NO_ALTERNATE),
|
||||
(u"telemetry lost", "telemko", NO_ALTERNATE),
|
||||
(u"telemetry recovered", "telemok", NO_ALTERNATE),
|
||||
(u"trainer signal lost", "trainko", NO_ALTERNATE),
|
||||
(u"trainer signal recovered", "trainok", NO_ALTERNATE),
|
||||
(u"sensor lost", "sensorko", NO_ALTERNATE),
|
||||
(u"servo overload", "servoko", NO_ALTERNATE),
|
||||
(u"power overload", "rxko", NO_ALTERNATE),
|
||||
for s, f, a in [("trim center", "midtrim", 495),
|
||||
("maximum trim reached", "maxtrim", NO_ALTERNATE),
|
||||
("minimum trim reached", "mintrim", NO_ALTERNATE),
|
||||
("timer 1 elapsed", "timovr1", NO_ALTERNATE),
|
||||
("timer 2 elapsed", "timovr2", NO_ALTERNATE),
|
||||
("timer 3 elapsed", "timovr3", NO_ALTERNATE),
|
||||
("transmitter battery low", "lowbatt", 485),
|
||||
("inactivity alarm", "inactiv", 486),
|
||||
("throttle warning", "thralert", 481),
|
||||
("switch warning", "swalert", 482),
|
||||
("bad eeprom", "eebad", 483),
|
||||
("Welcome to open tea ex!", "hello", 480),
|
||||
("RF signal, low", "rssi_org", NO_ALTERNATE),
|
||||
("RF signal, critical", "rssi_red", NO_ALTERNATE),
|
||||
("radio antenna defective", "swr_red", NO_ALTERNATE),
|
||||
("telemetry lost", "telemko", NO_ALTERNATE),
|
||||
("telemetry recovered", "telemok", NO_ALTERNATE),
|
||||
("trainer signal lost", "trainko", NO_ALTERNATE),
|
||||
("trainer signal recovered", "trainok", NO_ALTERNATE),
|
||||
("sensor lost", "sensorko", NO_ALTERNATE),
|
||||
("servo overload", "servoko", NO_ALTERNATE),
|
||||
("power overload", "rxko", NO_ALTERNATE),
|
||||
]:
|
||||
systemSounds.append((s, filename(f, a)))
|
||||
for i, (s, f) in enumerate([(u"gear!, up!", "gearup"),
|
||||
(u"gear!, down!", "geardn"),
|
||||
(u"flaps!, up!", "flapup"),
|
||||
(u"flaps!, down!", "flapdn"),
|
||||
(u"spoiler!, up!", "splrup"),
|
||||
(u"spoiler!, down!", "splrdn"),
|
||||
(u"trainer!, on!", "trnon"),
|
||||
(u"trainer!, off!", "trnoff"),
|
||||
(u"engine!, off!", "engoff"),
|
||||
(u"too. high!", "tohigh"),
|
||||
(u"too. low!", "tolow"),
|
||||
(u"low. battery!", "lowbat"),
|
||||
(u"crow!, on!", "crowon"),
|
||||
(u"crow!, off!", "crowof"),
|
||||
(u"rf. signal!, low!", "siglow"),
|
||||
(u"rf. signal!, critical!", "sigcrt"),
|
||||
(u"high. speed. mode!, active", "spdmod"),
|
||||
(u"thermal. mode!, on", "thmmod"),
|
||||
(u"normal. mode!, on", "nrmmod"),
|
||||
(u"landing. mode!, on", "lnding"),
|
||||
(u"acro. mode!, on", "acro"),
|
||||
(u"flight. mode!, one", "fm-1"),
|
||||
(u"flight. mode!, two", "fm-2"),
|
||||
(u"flight. mode!, three", "fm-3"),
|
||||
(u"flight. mode!, four", "fm-4"),
|
||||
(u"flight. mode!, five", "fm-5"),
|
||||
(u"flight. mode!, six", "fm-6"),
|
||||
(u"flight. mode!, seven", "fm-7"),
|
||||
(u"flight. mode!, eight", "fm-8"),
|
||||
(u"vario!, on", "vrion"),
|
||||
(u"vario!, off", "vrioff"),
|
||||
(u"flight mode!, power", "fm-pwr"),
|
||||
(u"flight mode!, land", "fm-lnd"),
|
||||
(u"flight mode!, float", "fm-flt"),
|
||||
(u"flight mode!, speed", "fm-spd"),
|
||||
(u"flight mode!, fast", "fm-fst"),
|
||||
(u"flight mode!, normal", "fm-nrm"),
|
||||
(u"flight mode!, cruise", "fm-crs"),
|
||||
(u"flight mode!, acro", "fm-acr"),
|
||||
(u"flight mode!, race", "fm-rce"),
|
||||
(u"flight mode!, launch", "fm-lch"),
|
||||
(u"flight mode!, ping", "fm-png"),
|
||||
(u"flight mode!, thermal", "fm-thm"),
|
||||
(u"flight mode!, thermal left", "fm-thl"),
|
||||
(u"flight mode!, thermal right", "fm-thr"),
|
||||
for i, (s, f) in enumerate([("gear!, up!", "gearup"),
|
||||
("gear!, down!", "geardn"),
|
||||
("flaps!, up!", "flapup"),
|
||||
("flaps!, down!", "flapdn"),
|
||||
("spoiler!, up!", "splrup"),
|
||||
("spoiler!, down!", "splrdn"),
|
||||
("trainer!, on!", "trnon"),
|
||||
("trainer!, off!", "trnoff"),
|
||||
("engine!, off!", "engoff"),
|
||||
("too. high!", "tohigh"),
|
||||
("too. low!", "tolow"),
|
||||
("low. battery!", "lowbat"),
|
||||
("crow!, on!", "crowon"),
|
||||
("crow!, off!", "crowof"),
|
||||
("rf. signal!, low!", "siglow"),
|
||||
("rf. signal!, critical!", "sigcrt"),
|
||||
("high. speed. mode!, active", "spdmod"),
|
||||
("thermal. mode!, on", "thmmod"),
|
||||
("normal. mode!, on", "nrmmod"),
|
||||
("landing. mode!, on", "lnding"),
|
||||
("acro. mode!, on", "acro"),
|
||||
("flight mode one", "fm-1"),
|
||||
("flight mode two", "fm-2"),
|
||||
("flight mode three", "fm-3"),
|
||||
("flight mode four", "fm-4"),
|
||||
("flight mode five", "fm-5"),
|
||||
("flight mode six", "fm-6"),
|
||||
("flight mode seven", "fm-7"),
|
||||
("flight mode eight", "fm-8"),
|
||||
("vario!, on", "vrion"),
|
||||
("vario!, off", "vrioff"),
|
||||
("flight mode power", "fm-pwr"),
|
||||
("flight mode land", "fm-lnd"),
|
||||
("flight mode float", "fm-flt"),
|
||||
("flight mode speed", "fm-spd"),
|
||||
("flight mode fast", "fm-fst"),
|
||||
("flight mode normal", "fm-nrm"),
|
||||
("flight mode cruise", "fm-crs"),
|
||||
("flight mode acro", "fm-acr"),
|
||||
("flight mode race", "fm-rce"),
|
||||
("flight mode launch", "fm-lch"),
|
||||
("flight mode ping", "fm-png"),
|
||||
("flight mode thermal", "fm-thm"),
|
||||
("flight mode thermal left", "fm-thl"),
|
||||
("flight mode thermal right", "fm-thr"),
|
||||
]):
|
||||
sounds.append((s, filename(f, PROMPT_CUSTOM_BASE + i)))
|
||||
|
||||
+80
-80
@@ -22,89 +22,89 @@ systemSounds.append(("nuevecientos", filename(PROMPT_SYSTEM_BASE + 109)))
|
||||
systemSounds.append(("mil", filename(PROMPT_SYSTEM_BASE + 110)))
|
||||
for i, s in enumerate(["coma", "un", "una", "y", "meno", "hora", "horas", "minuto", "minutos", "segundo", "segundos"]):
|
||||
systemSounds.append((s, filename(PROMPT_SYSTEM_BASE + 111 + i)))
|
||||
for i, (s, f) in enumerate([(u"Voltio","volt0"),
|
||||
(u"ampério", "amp0"),
|
||||
(u"miliamperios", "mamp0"),
|
||||
(u"knots", "knot0"),
|
||||
(u"metros por segundo", "mps0"),
|
||||
(u"pie por segundo", "fps0"),
|
||||
(u"kilómetro por hora", "kph0"),
|
||||
(u"millas por hora", "mph0"),
|
||||
(u"metros", "meter0"),
|
||||
(u"pie", "foot0"),
|
||||
(u"grados", "celsius0"),
|
||||
(u"fahrenheit", "fahr0"),
|
||||
(u"por ciento", "percent0"),
|
||||
(u"miliamperios por hora", "mamph0"),
|
||||
(u"vatio", "watt0"),
|
||||
(u"millivatio", "mwatt0"),
|
||||
(u"D B", "db0"),
|
||||
(u"R P M", "rpm0"),
|
||||
(u"g", "g0"),
|
||||
(u"grados", "degree0"),
|
||||
(u"radianes ", "rad0"),
|
||||
(u"mililitro", "ml0"),
|
||||
(u"onzas", "founce0"),
|
||||
(u"horas", "hour0"),
|
||||
(u"minutos", "minute0"),
|
||||
(u"segundos", "second0"),
|
||||
for i, (s, f) in enumerate([("Voltio","volt0"),
|
||||
("ampério", "amp0"),
|
||||
("miliamperios", "mamp0"),
|
||||
("knots", "knot0"),
|
||||
("metros por segundo", "mps0"),
|
||||
("pie por segundo", "fps0"),
|
||||
("kilómetro por hora", "kph0"),
|
||||
("millas por hora", "mph0"),
|
||||
("metros", "meter0"),
|
||||
("pie", "foot0"),
|
||||
("grados", "celsius0"),
|
||||
("fahrenheit", "fahr0"),
|
||||
("por ciento", "percent0"),
|
||||
("miliamperios por hora", "mamph0"),
|
||||
("vatio", "watt0"),
|
||||
("millivatio", "mwatt0"),
|
||||
("D B", "db0"),
|
||||
("R P M", "rpm0"),
|
||||
("g", "g0"),
|
||||
("grados", "degree0"),
|
||||
("radianes ", "rad0"),
|
||||
("mililitro", "ml0"),
|
||||
("onzas", "founce0"),
|
||||
("horas", "hour0"),
|
||||
("minutos", "minute0"),
|
||||
("segundos", "second0"),
|
||||
]):
|
||||
systemSounds.append((s, filename(f, PROMPT_SYSTEM_BASE + 122 + i)))
|
||||
for s, f, a in [(u"me tienes abandonada", "inactiv", 486),
|
||||
(u"batería del transmisor baja", "lowbatt", 485),
|
||||
(u"El acelerador está activado, por favor, corrijalo", "thralert", 481),
|
||||
(u"Los interruptores no están en la posición correcta, por favor corrijalo", "swalert", 482),
|
||||
(u"eeprom corrompida", "eebad", NO_ALTERNATE),
|
||||
(u"Formateo de eeprom en curso", "eeformat", NO_ALTERNATE),
|
||||
(u"error", "error", NO_ALTERNATE),
|
||||
(u"trim centrado", "midtrim", 495),
|
||||
(u"potenciómetro centrado", "midpot", 496),
|
||||
(u"trim al máximo", "maxtrim", NO_ALTERNATE),
|
||||
(u"trim al mínima", "mintrim", NO_ALTERNATE),
|
||||
(u"20 segundos", "timer20", 500),
|
||||
(u"30 segundos", "timer30", 501),
|
||||
(u"assorbimiento elevado", "highmah", NO_ALTERNATE),
|
||||
(u"temperatura elevada", "hightemp", NO_ALTERNATE),
|
||||
(u"Alarma A1", "a1_org", NO_ALTERNATE),
|
||||
(u"A1 crítica", "a1_red", NO_ALTERNATE),
|
||||
(u"Alarma A2", "a2_org", NO_ALTERNATE),
|
||||
(u"A2 crítica", "a2_red", NO_ALTERNATE),
|
||||
(u"recepcion de señal baja", "rssi_org", NO_ALTERNATE),
|
||||
(u"recepción de señal crítica", "rssi_red", NO_ALTERNATE),
|
||||
(u"Problemas con la antena del transmisor", "swr_red", NO_ALTERNATE),
|
||||
(u"Sin telemetría", "telemko", NO_ALTERNATE),
|
||||
(u"Telemetría disponible", "telemok", NO_ALTERNATE),
|
||||
systemSounds.append((s, filename(f, PROMPT_SYSTEM_BASE + 122 + i)))
|
||||
for s, f, a in [("me tienes abandonada", "inactiv", 486),
|
||||
("batería del transmisor baja", "lowbatt", 485),
|
||||
("El acelerador está activado, por favor, corrijalo", "thralert", 481),
|
||||
("Los interruptores no están en la posición correcta, por favor corrijalo", "swalert", 482),
|
||||
("eeprom corrompida", "eebad", NO_ALTERNATE),
|
||||
("Formateo de eeprom en curso", "eeformat", NO_ALTERNATE),
|
||||
("error", "error", NO_ALTERNATE),
|
||||
("trim centrado", "midtrim", 495),
|
||||
("potenciómetro centrado", "midpot", 496),
|
||||
("trim al máximo", "maxtrim", NO_ALTERNATE),
|
||||
("trim al mínima", "mintrim", NO_ALTERNATE),
|
||||
("20 segundos", "timer20", 500),
|
||||
("30 segundos", "timer30", 501),
|
||||
("assorbimiento elevado", "highmah", NO_ALTERNATE),
|
||||
("temperatura elevada", "hightemp", NO_ALTERNATE),
|
||||
("Alarma A1", "a1_org", NO_ALTERNATE),
|
||||
("A1 crítica", "a1_red", NO_ALTERNATE),
|
||||
("Alarma A2", "a2_org", NO_ALTERNATE),
|
||||
("A2 crítica", "a2_red", NO_ALTERNATE),
|
||||
("recepcion de señal baja", "rssi_org", NO_ALTERNATE),
|
||||
("recepción de señal crítica", "rssi_red", NO_ALTERNATE),
|
||||
("Problemas con la antena del transmisor", "swr_red", NO_ALTERNATE),
|
||||
("Sin telemetría", "telemko", NO_ALTERNATE),
|
||||
("Telemetría disponible", "telemok", NO_ALTERNATE),
|
||||
]:
|
||||
systemSounds.append((s, filename(f, a)))
|
||||
for i, s in enumerate([u"cronómetro", u"cronómetro", u"transmisión", u"recepción", u"A1", u"A2", u"altitud", u"motor",
|
||||
u"combustible", u"temperatura", u"temperatura", u"velocidad", u"distancia", u"altitude", u"célula lipo",
|
||||
u"Total lipo", u"voltaje", u"corriente", u"consumo", u"potencia", u"aceleración X", u"aceleración Y", u"aceleración Z",
|
||||
u"dirección", u"variómetro", u"minimo", u"máximo"]):
|
||||
for i, s in enumerate(["cronómetro", "cronómetro", "transmisión", "recepción", "A1", "A2", "altitud", "motor",
|
||||
"combustible", "temperatura", "temperatura", "velocidad", "distancia", "altitude", "célula lipo",
|
||||
"Total lipo", "voltaje", "corriente", "consumo", "potencia", "aceleración X", "aceleración Y", "aceleración Z",
|
||||
"dirección", "variómetro", "minimo", "máximo"]):
|
||||
systemSounds.append((s, filename(PROMPT_SYSTEM_BASE + 141 + i)))
|
||||
for i, (s, f) in enumerate([(u"tren arriba.", "gearup"),
|
||||
(u"tren abajo.", "geardn"),
|
||||
(u"flaps arriba", "flapup"),
|
||||
(u"flaps abajo", "flapdn"),
|
||||
(u"aterrizaje", "attero"),
|
||||
(u"modo de entrenamiento activado", "trnon"),
|
||||
(u"modo de entrenamiento deshabilitado", "trnoff"),
|
||||
(u"motor apagado", "engoff"),
|
||||
(u"muy alto", "tohigh"),
|
||||
(u"muy bajo", "tolow"),
|
||||
(u"bateria baja", "lowbat"),
|
||||
(u"crou, activo", "crowon"),
|
||||
(u"crou, desligado", "crowof"),
|
||||
(u"modo de velocidad", "spdmod"),
|
||||
(u"modo de térmica", "thmmod"),
|
||||
(u"modo de vuelo normal", "nrmmod"),
|
||||
(u"fase de vuelo 1", "fltmd1"),
|
||||
(u"fase de vuelo 2", "fltmd2"),
|
||||
(u"fase de vuelo 3", "fltmd3"),
|
||||
(u"fase de vuelo 4", "fltmd4"),
|
||||
(u"fase de vuelo 5", "fltmd5"),
|
||||
(u"fase de vuelo 6", "fltmd6"),
|
||||
(u"fase de vuelo 7", "fltmd7"),
|
||||
(u"fase de vuelo 8", "fltmd8"),
|
||||
(u"fase de vuelo 9", "fltmd9"),
|
||||
for i, (s, f) in enumerate([("tren arriba.", "gearup"),
|
||||
("tren abajo.", "geardn"),
|
||||
("flaps arriba", "flapup"),
|
||||
("flaps abajo", "flapdn"),
|
||||
("aterrizaje", "attero"),
|
||||
("modo de entrenamiento activado", "trnon"),
|
||||
("modo de entrenamiento deshabilitado", "trnoff"),
|
||||
("motor apagado", "engoff"),
|
||||
("muy alto", "tohigh"),
|
||||
("muy bajo", "tolow"),
|
||||
("bateria baja", "lowbat"),
|
||||
("crou, activo", "crowon"),
|
||||
("crou, desligado", "crowof"),
|
||||
("modo de velocidad", "spdmod"),
|
||||
("modo de térmica", "thmmod"),
|
||||
("modo de vuelo normal", "nrmmod"),
|
||||
("fase de vuelo 1", "fltmd1"),
|
||||
("fase de vuelo 2", "fltmd2"),
|
||||
("fase de vuelo 3", "fltmd3"),
|
||||
("fase de vuelo 4", "fltmd4"),
|
||||
("fase de vuelo 5", "fltmd5"),
|
||||
("fase de vuelo 6", "fltmd6"),
|
||||
("fase de vuelo 7", "fltmd7"),
|
||||
("fase de vuelo 8", "fltmd8"),
|
||||
("fase de vuelo 9", "fltmd9"),
|
||||
]):
|
||||
sounds.append((s, filename(f, PROMPT_CUSTOM_BASE + i)))
|
||||
|
||||
+88
-59
@@ -15,70 +15,99 @@ for i, s in enumerate(["une", "onze", "vingt et une", "trente et une", "quarante
|
||||
systemSounds.append((s, filename(PROMPT_SYSTEM_BASE + 110 + i)))
|
||||
for i, s in enumerate(["virgule", "et", "moins", "minuit", "midi"]):
|
||||
systemSounds.append((s, filename(PROMPT_SYSTEM_BASE + 119 + i)))
|
||||
for i, (s, f) in enumerate([(u"volts","volt0"),
|
||||
(u"ampères", "amp0"),
|
||||
(u"milli ampères", "mamp0"),
|
||||
(u"noeud", "knot0"),
|
||||
(u"mètres seconde", "mps0"),
|
||||
(u"pieds par seconde", "fps0"),
|
||||
(u"kilomètre heure", "kph0"),
|
||||
(u"miles par heure", "mph0"),
|
||||
(u"mètres", "meter0"),
|
||||
(u"pieds", "foot0"),
|
||||
(u"degrés", "celsius0"),
|
||||
(u"degrés fahrenheit", "degf0"),
|
||||
(u"pourcents", "percent0"),
|
||||
(u"milli ampères heure", "mamph0"),
|
||||
(u"watt", "watt0"),
|
||||
(u"milli watt", "mwatt0"),
|
||||
(u"d b", "db0"),
|
||||
(u"tours minute", "rpm0"),
|
||||
(u"g", "g0"),
|
||||
(u"degrés", "degree0"),
|
||||
(u"radians", "rad0"),
|
||||
(u"millilitres", "ml0"),
|
||||
(u"onces", "founce0"),
|
||||
(u"heure", "hour0"),
|
||||
(u"minute", "minute0"),
|
||||
(u"seconde", "second0"),
|
||||
for i, (s, f) in enumerate([("volts","volt0"),
|
||||
("ampères", "amp0"),
|
||||
("milli ampères", "mamp0"),
|
||||
("noeud", "knot0"),
|
||||
("mètres seconde", "mps0"),
|
||||
("pieds par seconde", "fps0"),
|
||||
("kilomètre heure", "kph0"),
|
||||
("miles par heure", "mph0"),
|
||||
("mètres", "meter0"),
|
||||
("pieds", "foot0"),
|
||||
("degrés", "celsius0"),
|
||||
("degrés fahrenheit", "degf0"),
|
||||
("pourcents", "percent0"),
|
||||
("milli ampères heure", "mamph0"),
|
||||
("watt", "watt0"),
|
||||
("milli watt", "mwatt0"),
|
||||
("d b", "db0"),
|
||||
("tours minute", "rpm0"),
|
||||
("g", "g0"),
|
||||
("degrés", "degree0"),
|
||||
("radians", "rad0"),
|
||||
("millilitres", "ml0"),
|
||||
("onces", "founce0"),
|
||||
("heure", "hour0"),
|
||||
("minute", "minute0"),
|
||||
("seconde", "second0"),
|
||||
]):
|
||||
systemSounds.append((s, filename(f, PROMPT_SYSTEM_BASE + 125 + i)))
|
||||
for i, s in enumerate(["virgule 0", "virgule 1", "virgule 2", "virgule 3", "virgule 4", "virgule 5", "virgule 6", "virgule 7", "virgule 8", "virgule 9"]):
|
||||
systemSounds.append((s, filename(PROMPT_SYSTEM_BASE + 180 + i)))
|
||||
for s, f, a in [(u"Trim centré", "midtrim", 495),
|
||||
(u"Trim maximum atteint", "maxtrim", NO_ALTERNATE),
|
||||
(u"Trim minimum atteint", "mintrim", NO_ALTERNATE),
|
||||
(u"Chrono 1 à 0", "timovr1", NO_ALTERNATE),
|
||||
(u"Chrono 2 à 0", "timovr2", NO_ALTERNATE),
|
||||
(u"Chrono 3 à 0", "timovr3", NO_ALTERNATE),
|
||||
(u"Batterie radio faible !", "lowbatt", 485),
|
||||
(u"Radio inactive !", "inactiv", 486),
|
||||
(u"Alerte manche des gaz", "thralert", 481),
|
||||
(u"Alerte inters", "swalert", 482),
|
||||
(u"éprome corrompue", "eebad", 483),
|
||||
(u"Bienvenue sur Open Thé Hix!", "hello", 480),
|
||||
(u"Signal RF, faible", "rssi_org", NO_ALTERNATE),
|
||||
(u"Signal RF, critique", "rssi_red", NO_ALTERNATE),
|
||||
(u"Antenne défectueuse", "swr_red", NO_ALTERNATE),
|
||||
(u"Plus de télémétrie", "telemko", NO_ALTERNATE),
|
||||
(u"Télémétrie retrouvée", "telemok", NO_ALTERNATE),
|
||||
(u"Signal écolage perdu", "trainko", NO_ALTERNATE),
|
||||
(u"Signal écolage retrouvé", "trainok", NO_ALTERNATE),
|
||||
(u"Sonde de télémétrie perdue", "sensorko", NO_ALTERNATE),
|
||||
(u"Servo en surcharge", "servoko", NO_ALTERNATE),
|
||||
(u"Surcharge réception", "rxko", NO_ALTERNATE),
|
||||
for s, f, a in [("Trim centré", "midtrim", 495),
|
||||
("Trim maximum atteint", "maxtrim", NO_ALTERNATE),
|
||||
("Trim minimum atteint", "mintrim", NO_ALTERNATE),
|
||||
("Chrono 1 à 0", "timovr1", NO_ALTERNATE),
|
||||
("Chrono 2 à 0", "timovr2", NO_ALTERNATE),
|
||||
("Chrono 3 à 0", "timovr3", NO_ALTERNATE),
|
||||
("Batterie radio faible !", "lowbatt", 485),
|
||||
("Radio inactive !", "inactiv", 486),
|
||||
("Alerte manche des gaz", "thralert", 481),
|
||||
("Alerte inters", "swalert", 482),
|
||||
("éprome corrompue", "eebad", 483),
|
||||
("Bienvenue sur o pun t x", "hello", 480),
|
||||
("Signal RF, faible", "rssi_org", NO_ALTERNATE),
|
||||
("Signal RF, critique", "rssi_red", NO_ALTERNATE),
|
||||
("Antenne défectueuse", "swr_red", NO_ALTERNATE),
|
||||
("Plus de télémétrie", "telemko", NO_ALTERNATE),
|
||||
("Télémétrie retrouvée", "telemok", NO_ALTERNATE),
|
||||
("Signal écolage perdu", "trainko", NO_ALTERNATE),
|
||||
("Signal écolage retrouvé", "trainok", NO_ALTERNATE),
|
||||
("Sonde de télémétrie perdue", "sensorko", NO_ALTERNATE),
|
||||
("Servo en surcharge", "servoko", NO_ALTERNATE),
|
||||
("Surcharge réception", "rxko", NO_ALTERNATE),
|
||||
]:
|
||||
systemSounds.append((s, filename(f, a)))
|
||||
for i, (s, f) in enumerate([(u"altitude", "altitude"),
|
||||
(u"température moteur", "moteur"),
|
||||
(u"température contrôleur", "cntrleur"),
|
||||
(u"train rentré", "gearup"),
|
||||
(u"train sorti", "geardn"),
|
||||
(u"volets rentrés", "flapup"),
|
||||
(u"volets sortis", "flapdn"),
|
||||
(u"atterrissage", "attero"),
|
||||
(u"écolage", "trnon"),
|
||||
(u"fin écolage", "trnoff"),
|
||||
(u"moteur coupé", "engoff"),
|
||||
for i, (s, f) in enumerate([("altitude", "altitude"),
|
||||
("température moteur", "moteur"),
|
||||
("température contrôleur", "cntrleur"),
|
||||
("train rentré", "gearup"),
|
||||
("train sorti", "geardn"),
|
||||
("volets rentrés", "flapup"),
|
||||
("volets sortis", "flapdn"),
|
||||
("atterrissage", "attero"),
|
||||
("écolage", "trnon"),
|
||||
("fin écolage", "trnoff"),
|
||||
("moteur coupé", "engoff"),
|
||||
("high. speed. mode!, active", "spdmod"),
|
||||
("thermal. mode!, on", "thmmod"),
|
||||
("normal. mode!, on", "nrmmod"),
|
||||
("landing. mode!, on", "lnding"),
|
||||
("mode acro", "acro"),
|
||||
("mode de vol un", "fm-1"),
|
||||
("mode de vol deux", "fm-2"),
|
||||
("mode de vol trois", "fm-3"),
|
||||
("mode de vol quatre", "fm-4"),
|
||||
("mode de vol 5", "fm-5"),
|
||||
("mode de vol 6", "fm-6"),
|
||||
("mode de vol sept", "fm-7"),
|
||||
("mode de vol 8", "fm-8"),
|
||||
("vario activé", "vrion"),
|
||||
("vario désactivé", "vrioff"),
|
||||
("mode de vol puissance", "fm-pwr"),
|
||||
("mode de vol attérissage", "fm-lnd"),
|
||||
("mode de vol amérissage", "fm-flt"),
|
||||
("mode de vol vitesse", "fm-spd"),
|
||||
("mode de vol rapide", "fm-fst"),
|
||||
("mode de vol normal", "fm-nrm"),
|
||||
("mode de vol de croisière", "fm-crs"),
|
||||
("mode de vol acro", "fm-acr"),
|
||||
("mode de vol course", "fm-rce"),
|
||||
("mode de vol lancé", "fm-lch"),
|
||||
("mode de vol ping", "fm-png"),
|
||||
("mode de vol thermique", "fm-thm"),
|
||||
("mode de vol thermique gauche", "fm-thl"),
|
||||
("mode de vol thermique droit", "fm-thr"),
|
||||
]):
|
||||
sounds.append((s, filename(f, PROMPT_CUSTOM_BASE + i)))
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user