From 408d0ef26dee248feffcc6354a69d808f8feaa39 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Mon, 17 Feb 2014 14:41:33 +0100 Subject: [PATCH 01/89] Allow 110Hz tones --- radio/src/audio_arm.cpp | 186 +++++++++++++++++++++++++++++----------- radio/src/audio_arm.h | 10 +-- 2 files changed, 142 insertions(+), 54 deletions(-) diff --git a/radio/src/audio_arm.cpp b/radio/src/audio_arm.cpp index 5d2fb1be9..b656ead9c 100644 --- a/radio/src/audio_arm.cpp +++ b/radio/src/audio_arm.cpp @@ -41,23 +41,112 @@ extern OS_MutexID audioMutex; const int16_t sineValues[] = { - 0, 64, 128, 191, 254, 316, 376, 435, 493, 548, - 601, 652, 700, 746, 789, 828, 864, 897, 926, 952, - 973, 991, 1005, 1015, 1021, 1024, 1021, 1015, 1005, 991, - 973, 952, 926, 897, 864, 828, 789, 746, 700, 652, - 601, 548, 493, 435, 376, 316, 254, 191, 128, 64, - 0, -64, -128, -191, -254, -316, -376, -435, -493, -548, - -601, -652, -700, -746, -789, -828, -864, -897, -926, -952, - -973, -991, -1005, -1015, -1021, -1024, -1021, -1015, -1005, -991, - -973, -952, -926, -897, -864, -828, -789, -746, -700, -652, - -601, -548, -493, -435, -376, -316, -254, -191, -128, -64, + 0, 6, 12, 18, 25, 31, 37, 43, 50, 56, + 62, 69, 75, 81, 87, 94, 100, 106, 112, 119, + 125, 131, 137, 144, 150, 156, 162, 168, 175, 181, + 187, 193, 199, 205, 212, 218, 224, 230, 236, 242, + 248, 254, 260, 267, 273, 279, 285, 291, 297, 303, + 309, 315, 321, 327, 333, 339, 344, 350, 356, 362, + 368, 374, 380, 386, 391, 397, 403, 409, 414, 420, + 426, 432, 437, 443, 449, 454, 460, 466, 471, 477, + 482, 488, 493, 499, 504, 510, 515, 521, 526, 531, + 537, 542, 547, 553, 558, 563, 568, 574, 579, 584, + 589, 594, 599, 604, 609, 615, 620, 625, 629, 634, + 639, 644, 649, 654, 659, 664, 668, 673, 678, 683, + 687, 692, 696, 701, 706, 710, 715, 719, 724, 728, + 732, 737, 741, 745, 750, 754, 758, 762, 767, 771, + 775, 779, 783, 787, 791, 795, 799, 803, 807, 811, + 814, 818, 822, 826, 829, 833, 837, 840, 844, 847, + 851, 854, 858, 861, 865, 868, 871, 875, 878, 881, + 884, 887, 890, 894, 897, 900, 903, 906, 908, 911, + 914, 917, 920, 922, 925, 928, 930, 933, 936, 938, + 941, 943, 946, 948, 950, 953, 955, 957, 959, 962, + 964, 966, 968, 970, 972, 974, 976, 978, 979, 981, + 983, 985, 986, 988, 990, 991, 993, 994, 996, 997, + 999, 1000, 1001, 1003, 1004, 1005, 1006, 1007, 1008, 1009, + 1010, 1011, 1012, 1013, 1014, 1015, 1016, 1017, 1017, 1018, + 1019, 1019, 1020, 1020, 1021, 1021, 1022, 1022, 1022, 1023, + 1023, 1023, 1023, 1023, 1023, 1023, 1024, 1023, 1023, 1023, + 1023, 1023, 1023, 1023, 1022, 1022, 1022, 1021, 1021, 1020, + 1020, 1019, 1019, 1018, 1017, 1017, 1016, 1015, 1014, 1013, + 1012, 1011, 1010, 1009, 1008, 1007, 1006, 1005, 1004, 1003, + 1001, 1000, 999, 997, 996, 994, 993, 991, 990, 988, + 986, 985, 983, 981, 979, 978, 976, 974, 972, 970, + 968, 966, 964, 962, 959, 957, 955, 953, 950, 948, + 946, 943, 941, 938, 936, 933, 930, 928, 925, 922, + 920, 917, 914, 911, 908, 906, 903, 900, 897, 894, + 890, 887, 884, 881, 878, 875, 871, 868, 865, 861, + 858, 854, 851, 847, 844, 840, 837, 833, 829, 826, + 822, 818, 814, 811, 807, 803, 799, 795, 791, 787, + 783, 779, 775, 771, 767, 762, 758, 754, 750, 745, + 741, 737, 732, 728, 724, 719, 715, 710, 706, 701, + 696, 692, 687, 683, 678, 673, 668, 664, 659, 654, + 649, 644, 639, 634, 629, 625, 620, 615, 609, 604, + 599, 594, 589, 584, 579, 574, 568, 563, 558, 553, + 547, 542, 537, 531, 526, 521, 515, 510, 504, 499, + 493, 488, 482, 477, 471, 466, 460, 454, 449, 443, + 437, 432, 426, 420, 414, 409, 403, 397, 391, 386, + 380, 374, 368, 362, 356, 350, 344, 339, 333, 327, + 321, 315, 309, 303, 297, 291, 285, 279, 273, 267, + 260, 254, 248, 242, 236, 230, 224, 218, 212, 205, + 199, 193, 187, 181, 175, 168, 162, 156, 150, 144, + 137, 131, 125, 119, 112, 106, 100, 94, 87, 81, + 75, 69, 62, 56, 50, 43, 37, 31, 25, 18, + 12, 6, 0, -6, -12, -18, -25, -31, -37, -43, + -50, -56, -62, -69, -75, -81, -87, -94, -100, -106, + -112, -119, -125, -131, -137, -144, -150, -156, -162, -168, + -175, -181, -187, -193, -199, -205, -212, -218, -224, -230, + -236, -242, -248, -254, -260, -267, -273, -279, -285, -291, + -297, -303, -309, -315, -321, -327, -333, -339, -344, -350, + -356, -362, -368, -374, -380, -386, -391, -397, -403, -409, + -414, -420, -426, -432, -437, -443, -449, -454, -460, -466, + -471, -477, -482, -488, -493, -499, -504, -510, -515, -521, + -526, -531, -537, -542, -547, -553, -558, -563, -568, -574, + -579, -584, -589, -594, -599, -604, -609, -615, -620, -625, + -629, -634, -639, -644, -649, -654, -659, -664, -668, -673, + -678, -683, -687, -692, -696, -701, -706, -710, -715, -719, + -724, -728, -732, -737, -741, -745, -750, -754, -758, -762, + -767, -771, -775, -779, -783, -787, -791, -795, -799, -803, + -807, -811, -814, -818, -822, -826, -829, -833, -837, -840, + -844, -847, -851, -854, -858, -861, -865, -868, -871, -875, + -878, -881, -884, -887, -890, -894, -897, -900, -903, -906, + -908, -911, -914, -917, -920, -922, -925, -928, -930, -933, + -936, -938, -941, -943, -946, -948, -950, -953, -955, -957, + -959, -962, -964, -966, -968, -970, -972, -974, -976, -978, + -979, -981, -983, -985, -986, -988, -990, -991, -993, -994, + -996, -997, -999, -1000, -1001, -1003, -1004, -1005, -1006, -1007, + -1008, -1009, -1010, -1011, -1012, -1013, -1014, -1015, -1016, -1017, + -1017, -1018, -1019, -1019, -1020, -1020, -1021, -1021, -1022, -1022, + -1022, -1023, -1023, -1023, -1023, -1023, -1023, -1023, -1024, -1023, + -1023, -1023, -1023, -1023, -1023, -1023, -1022, -1022, -1022, -1021, + -1021, -1020, -1020, -1019, -1019, -1018, -1017, -1017, -1016, -1015, + -1014, -1013, -1012, -1011, -1010, -1009, -1008, -1007, -1006, -1005, + -1004, -1003, -1001, -1000, -999, -997, -996, -994, -993, -991, + -990, -988, -986, -985, -983, -981, -979, -978, -976, -974, + -972, -970, -968, -966, -964, -962, -959, -957, -955, -953, + -950, -948, -946, -943, -941, -938, -936, -933, -930, -928, + -925, -922, -920, -917, -914, -911, -908, -906, -903, -900, + -897, -894, -890, -887, -884, -881, -878, -875, -871, -868, + -865, -861, -858, -854, -851, -847, -844, -840, -837, -833, + -829, -826, -822, -818, -814, -811, -807, -803, -799, -795, + -791, -787, -783, -779, -775, -771, -767, -762, -758, -754, + -750, -745, -741, -737, -732, -728, -724, -719, -715, -710, + -706, -701, -696, -692, -687, -683, -678, -673, -668, -664, + -659, -654, -649, -644, -639, -634, -629, -625, -620, -615, + -609, -604, -599, -594, -589, -584, -579, -574, -568, -563, + -558, -553, -547, -542, -537, -531, -526, -521, -515, -510, + -504, -499, -493, -488, -482, -477, -471, -466, -460, -454, + -449, -443, -437, -432, -426, -420, -414, -409, -403, -397, + -391, -386, -380, -374, -368, -362, -356, -350, -344, -339, + -333, -327, -321, -315, -309, -303, -297, -291, -285, -279, + -273, -267, -260, -254, -248, -242, -236, -230, -224, -218, + -212, -205, -199, -193, -187, -181, -175, -168, -162, -156, + -150, -144, -137, -131, -125, -119, -112, -106, -100, -94, + -87, -81, -75, -69, -62, -56, -50, -43, -37, -31, + -25, -18, -12, -6, }; -#if 1 - const unsigned int toneVolumes[] = { 2, 4, 8, 12, 16 }; -#else - const unsigned int toneVolumes[] = { 4000, 8000, 16000, 24000, 32000 }; -#endif +const unsigned int toneVolumes[] = { 2, 4, 8, 12, 16 }; #if defined(SDCARD) const char * audioFilenames[] = { @@ -459,48 +548,49 @@ int AudioQueue::mixBeep(AudioContext &context, AudioBuffer *buffer, int volume, int result = 0; if (fragment.tone.duration > 0) { - result = AUDIO_BUFFER_SIZE; - if (fragment.tone.freq && context.state.tone.freq!=fragment.tone.freq && (!fragment.tone.freqIncr || abs(context.state.tone.freq-fragment.tone.freq) > 100)) { - int periods = BEEP_POINTS_COUNT / ((AUDIO_SAMPLE_RATE / fragment.tone.freq) + 1); - context.state.tone.count = (periods * AUDIO_SAMPLE_RATE) / fragment.tone.freq; - if (context.state.tone.idx >= context.state.tone.count) context.state.tone.idx = 0; -#if 1 - for (unsigned int i=0; i DIM(sineValues)) + end -= (end % DIM(sineValues)); + else + end = DIM(sineValues); + points = (double(end) - toneIdx) / context.state.tone.step; + } + else { + duration = AUDIO_BUFFER_DURATION; + fragment.tone.duration -= AUDIO_BUFFER_DURATION; + points = AUDIO_BUFFER_SIZE; } for (int i=0; idata[i], context.state.tone.points[context.state.tone.idx], fade); - context.state.tone.idx = context.state.tone.idx + 1; - if (context.state.tone.idx >= context.state.tone.count) { - context.state.tone.idx = 0; - if (end && i+BEEP_POINTS_COUNT>points) break; - } + int16_t sample = sineValues[int(toneIdx)] * toneVolumes[2+volume]; + mix(&buffer->data[i], sample, fade); + toneIdx += context.state.tone.step; + if ((unsigned int)toneIdx >= DIM(sineValues)) + toneIdx -= DIM(sineValues); } - fragment.tone.duration -= duration; - if (fragment.tone.duration > 0) + if (fragment.tone.duration > 0) { + context.state.tone.idx = toneIdx; return AUDIO_BUFFER_SIZE; + } + else { + context.state.tone.idx = 0; + } } if (fragment.tone.pause > 0) { @@ -548,7 +638,7 @@ void AudioQueue::wakeup() // mix the foreground context result = mixAudioContext(foregroundContext, buffer, g_eeGeneral.beepVolume, g_eeGeneral.wavVolume, fade); if (result > 0) { - size = max(size, result); + size = result; fade += 1; } diff --git a/radio/src/audio_arm.h b/radio/src/audio_arm.h index 9b45187b0..fadceeb59 100644 --- a/radio/src/audio_arm.h +++ b/radio/src/audio_arm.h @@ -47,11 +47,10 @@ #define AUDIO_BUFFER_SIZE (AUDIO_SAMPLE_RATE*AUDIO_BUFFER_DURATION/1000) #define AUDIO_BUFFER_COUNT (3) -#define BEEP_MIN_FREQ (440) +#define BEEP_MIN_FREQ (110) #define BEEP_DEFAULT_FREQ (2250) #define BEEP_KEY_UP_FREQ (BEEP_DEFAULT_FREQ+150) #define BEEP_KEY_DOWN_FREQ (BEEP_DEFAULT_FREQ-150) -#define BEEP_POINTS_COUNT 100 #define AUDIO_BUFFER_FREE (0) #define AUDIO_BUFFER_FILLED (1) @@ -105,10 +104,9 @@ class AudioContext { #endif struct { - int16_t points[BEEP_POINTS_COUNT]; - uint8_t count; - uint8_t idx; - uint16_t freq; + double step; + double idx; + double volume; } tone; } state; From 502ea0e9215e35ddb0848ac14fde944b2619d395 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Mon, 17 Feb 2014 15:19:05 +0100 Subject: [PATCH 02/89] Lower sounds must have a greater amplitude in order to have the same energy --- radio/src/audio_arm.cpp | 213 ++++++++++++++++++++-------------------- radio/src/audio_arm.h | 2 +- 2 files changed, 108 insertions(+), 107 deletions(-) diff --git a/radio/src/audio_arm.cpp b/radio/src/audio_arm.cpp index b656ead9c..45b53ba67 100644 --- a/radio/src/audio_arm.cpp +++ b/radio/src/audio_arm.cpp @@ -41,113 +41,111 @@ extern OS_MutexID audioMutex; const int16_t sineValues[] = { - 0, 6, 12, 18, 25, 31, 37, 43, 50, 56, - 62, 69, 75, 81, 87, 94, 100, 106, 112, 119, - 125, 131, 137, 144, 150, 156, 162, 168, 175, 181, - 187, 193, 199, 205, 212, 218, 224, 230, 236, 242, - 248, 254, 260, 267, 273, 279, 285, 291, 297, 303, - 309, 315, 321, 327, 333, 339, 344, 350, 356, 362, - 368, 374, 380, 386, 391, 397, 403, 409, 414, 420, - 426, 432, 437, 443, 449, 454, 460, 466, 471, 477, - 482, 488, 493, 499, 504, 510, 515, 521, 526, 531, - 537, 542, 547, 553, 558, 563, 568, 574, 579, 584, - 589, 594, 599, 604, 609, 615, 620, 625, 629, 634, - 639, 644, 649, 654, 659, 664, 668, 673, 678, 683, - 687, 692, 696, 701, 706, 710, 715, 719, 724, 728, - 732, 737, 741, 745, 750, 754, 758, 762, 767, 771, - 775, 779, 783, 787, 791, 795, 799, 803, 807, 811, - 814, 818, 822, 826, 829, 833, 837, 840, 844, 847, - 851, 854, 858, 861, 865, 868, 871, 875, 878, 881, - 884, 887, 890, 894, 897, 900, 903, 906, 908, 911, - 914, 917, 920, 922, 925, 928, 930, 933, 936, 938, - 941, 943, 946, 948, 950, 953, 955, 957, 959, 962, - 964, 966, 968, 970, 972, 974, 976, 978, 979, 981, - 983, 985, 986, 988, 990, 991, 993, 994, 996, 997, - 999, 1000, 1001, 1003, 1004, 1005, 1006, 1007, 1008, 1009, - 1010, 1011, 1012, 1013, 1014, 1015, 1016, 1017, 1017, 1018, - 1019, 1019, 1020, 1020, 1021, 1021, 1022, 1022, 1022, 1023, - 1023, 1023, 1023, 1023, 1023, 1023, 1024, 1023, 1023, 1023, - 1023, 1023, 1023, 1023, 1022, 1022, 1022, 1021, 1021, 1020, - 1020, 1019, 1019, 1018, 1017, 1017, 1016, 1015, 1014, 1013, - 1012, 1011, 1010, 1009, 1008, 1007, 1006, 1005, 1004, 1003, - 1001, 1000, 999, 997, 996, 994, 993, 991, 990, 988, - 986, 985, 983, 981, 979, 978, 976, 974, 972, 970, - 968, 966, 964, 962, 959, 957, 955, 953, 950, 948, - 946, 943, 941, 938, 936, 933, 930, 928, 925, 922, - 920, 917, 914, 911, 908, 906, 903, 900, 897, 894, - 890, 887, 884, 881, 878, 875, 871, 868, 865, 861, - 858, 854, 851, 847, 844, 840, 837, 833, 829, 826, - 822, 818, 814, 811, 807, 803, 799, 795, 791, 787, - 783, 779, 775, 771, 767, 762, 758, 754, 750, 745, - 741, 737, 732, 728, 724, 719, 715, 710, 706, 701, - 696, 692, 687, 683, 678, 673, 668, 664, 659, 654, - 649, 644, 639, 634, 629, 625, 620, 615, 609, 604, - 599, 594, 589, 584, 579, 574, 568, 563, 558, 553, - 547, 542, 537, 531, 526, 521, 515, 510, 504, 499, - 493, 488, 482, 477, 471, 466, 460, 454, 449, 443, - 437, 432, 426, 420, 414, 409, 403, 397, 391, 386, - 380, 374, 368, 362, 356, 350, 344, 339, 333, 327, - 321, 315, 309, 303, 297, 291, 285, 279, 273, 267, - 260, 254, 248, 242, 236, 230, 224, 218, 212, 205, - 199, 193, 187, 181, 175, 168, 162, 156, 150, 144, - 137, 131, 125, 119, 112, 106, 100, 94, 87, 81, - 75, 69, 62, 56, 50, 43, 37, 31, 25, 18, - 12, 6, 0, -6, -12, -18, -25, -31, -37, -43, - -50, -56, -62, -69, -75, -81, -87, -94, -100, -106, - -112, -119, -125, -131, -137, -144, -150, -156, -162, -168, - -175, -181, -187, -193, -199, -205, -212, -218, -224, -230, - -236, -242, -248, -254, -260, -267, -273, -279, -285, -291, - -297, -303, -309, -315, -321, -327, -333, -339, -344, -350, - -356, -362, -368, -374, -380, -386, -391, -397, -403, -409, - -414, -420, -426, -432, -437, -443, -449, -454, -460, -466, - -471, -477, -482, -488, -493, -499, -504, -510, -515, -521, - -526, -531, -537, -542, -547, -553, -558, -563, -568, -574, - -579, -584, -589, -594, -599, -604, -609, -615, -620, -625, - -629, -634, -639, -644, -649, -654, -659, -664, -668, -673, - -678, -683, -687, -692, -696, -701, -706, -710, -715, -719, - -724, -728, -732, -737, -741, -745, -750, -754, -758, -762, - -767, -771, -775, -779, -783, -787, -791, -795, -799, -803, - -807, -811, -814, -818, -822, -826, -829, -833, -837, -840, - -844, -847, -851, -854, -858, -861, -865, -868, -871, -875, - -878, -881, -884, -887, -890, -894, -897, -900, -903, -906, - -908, -911, -914, -917, -920, -922, -925, -928, -930, -933, - -936, -938, -941, -943, -946, -948, -950, -953, -955, -957, - -959, -962, -964, -966, -968, -970, -972, -974, -976, -978, - -979, -981, -983, -985, -986, -988, -990, -991, -993, -994, - -996, -997, -999, -1000, -1001, -1003, -1004, -1005, -1006, -1007, - -1008, -1009, -1010, -1011, -1012, -1013, -1014, -1015, -1016, -1017, - -1017, -1018, -1019, -1019, -1020, -1020, -1021, -1021, -1022, -1022, - -1022, -1023, -1023, -1023, -1023, -1023, -1023, -1023, -1024, -1023, - -1023, -1023, -1023, -1023, -1023, -1023, -1022, -1022, -1022, -1021, - -1021, -1020, -1020, -1019, -1019, -1018, -1017, -1017, -1016, -1015, - -1014, -1013, -1012, -1011, -1010, -1009, -1008, -1007, -1006, -1005, - -1004, -1003, -1001, -1000, -999, -997, -996, -994, -993, -991, - -990, -988, -986, -985, -983, -981, -979, -978, -976, -974, - -972, -970, -968, -966, -964, -962, -959, -957, -955, -953, - -950, -948, -946, -943, -941, -938, -936, -933, -930, -928, - -925, -922, -920, -917, -914, -911, -908, -906, -903, -900, - -897, -894, -890, -887, -884, -881, -878, -875, -871, -868, - -865, -861, -858, -854, -851, -847, -844, -840, -837, -833, - -829, -826, -822, -818, -814, -811, -807, -803, -799, -795, - -791, -787, -783, -779, -775, -771, -767, -762, -758, -754, - -750, -745, -741, -737, -732, -728, -724, -719, -715, -710, - -706, -701, -696, -692, -687, -683, -678, -673, -668, -664, - -659, -654, -649, -644, -639, -634, -629, -625, -620, -615, - -609, -604, -599, -594, -589, -584, -579, -574, -568, -563, - -558, -553, -547, -542, -537, -531, -526, -521, -515, -510, - -504, -499, -493, -488, -482, -477, -471, -466, -460, -454, - -449, -443, -437, -432, -426, -420, -414, -409, -403, -397, - -391, -386, -380, -374, -368, -362, -356, -350, -344, -339, - -333, -327, -321, -315, -309, -303, -297, -291, -285, -279, - -273, -267, -260, -254, -248, -242, -236, -230, -224, -218, - -212, -205, -199, -193, -187, -181, -175, -168, -162, -156, - -150, -144, -137, -131, -125, -119, -112, -106, -100, -94, - -87, -81, -75, -69, -62, -56, -50, -43, -37, -31, - -25, -18, -12, -6, + 0, 201, 402, 603, 804, 1005, 1206, 1406, 1607, 1808, + 2009, 2209, 2410, 2610, 2811, 3011, 3211, 3411, 3611, 3811, + 4011, 4210, 4409, 4609, 4807, 5006, 5205, 5403, 5601, 5799, + 5997, 6195, 6392, 6589, 6786, 6983, 7179, 7375, 7571, 7766, + 7961, 8156, 8351, 8545, 8739, 8933, 9126, 9319, 9511, 9704, + 9895, 10087, 10278, 10469, 10659, 10849, 11039, 11228, 11416, 11605, + 11792, 11980, 12167, 12353, 12539, 12725, 12910, 13094, 13278, 13462, + 13645, 13827, 14009, 14191, 14372, 14552, 14732, 14911, 15090, 15268, + 15446, 15623, 15799, 15975, 16151, 16325, 16499, 16673, 16845, 17017, + 17189, 17360, 17530, 17700, 17868, 18037, 18204, 18371, 18537, 18703, + 18867, 19031, 19195, 19357, 19519, 19680, 19841, 20000, 20159, 20317, + 20475, 20631, 20787, 20942, 21096, 21250, 21402, 21554, 21705, 21855, + 22005, 22153, 22301, 22448, 22594, 22739, 22884, 23027, 23170, 23311, + 23452, 23592, 23731, 23869, 24007, 24143, 24279, 24413, 24547, 24680, + 24811, 24942, 25072, 25201, 25329, 25456, 25582, 25707, 25832, 25955, + 26077, 26198, 26319, 26438, 26556, 26673, 26790, 26905, 27019, 27132, + 27245, 27356, 27466, 27575, 27683, 27790, 27896, 28001, 28105, 28208, + 28310, 28410, 28510, 28609, 28706, 28803, 28898, 28992, 29085, 29177, + 29268, 29358, 29447, 29534, 29621, 29706, 29791, 29874, 29956, 30037, + 30117, 30195, 30273, 30349, 30424, 30498, 30571, 30643, 30714, 30783, + 30852, 30919, 30985, 31050, 31113, 31176, 31237, 31297, 31356, 31414, + 31470, 31526, 31580, 31633, 31685, 31736, 31785, 31833, 31880, 31926, + 31971, 32014, 32057, 32098, 32137, 32176, 32213, 32250, 32285, 32318, + 32351, 32382, 32412, 32441, 32469, 32495, 32521, 32545, 32567, 32589, + 32609, 32628, 32646, 32663, 32678, 32692, 32705, 32717, 32728, 32737, + 32745, 32752, 32757, 32761, 32765, 32766, 32767, 32766, 32765, 32761, + 32757, 32752, 32745, 32737, 32728, 32717, 32705, 32692, 32678, 32663, + 32646, 32628, 32609, 32589, 32567, 32545, 32521, 32495, 32469, 32441, + 32412, 32382, 32351, 32318, 32285, 32250, 32213, 32176, 32137, 32098, + 32057, 32014, 31971, 31926, 31880, 31833, 31785, 31736, 31685, 31633, + 31580, 31526, 31470, 31414, 31356, 31297, 31237, 31176, 31113, 31050, + 30985, 30919, 30852, 30783, 30714, 30643, 30571, 30498, 30424, 30349, + 30273, 30195, 30117, 30037, 29956, 29874, 29791, 29706, 29621, 29534, + 29447, 29358, 29268, 29177, 29085, 28992, 28898, 28803, 28706, 28609, + 28510, 28410, 28310, 28208, 28105, 28001, 27896, 27790, 27683, 27575, + 27466, 27356, 27245, 27132, 27019, 26905, 26790, 26673, 26556, 26438, + 26319, 26198, 26077, 25955, 25832, 25707, 25582, 25456, 25329, 25201, + 25072, 24942, 24811, 24680, 24547, 24413, 24279, 24143, 24007, 23869, + 23731, 23592, 23452, 23311, 23170, 23027, 22884, 22739, 22594, 22448, + 22301, 22153, 22005, 21855, 21705, 21554, 21402, 21250, 21096, 20942, + 20787, 20631, 20475, 20317, 20159, 20000, 19841, 19680, 19519, 19357, + 19195, 19031, 18867, 18703, 18537, 18371, 18204, 18037, 17868, 17700, + 17530, 17360, 17189, 17017, 16845, 16673, 16499, 16325, 16151, 15975, + 15799, 15623, 15446, 15268, 15090, 14911, 14732, 14552, 14372, 14191, + 14009, 13827, 13645, 13462, 13278, 13094, 12910, 12725, 12539, 12353, + 12167, 11980, 11792, 11605, 11416, 11228, 11039, 10849, 10659, 10469, + 10278, 10087, 9895, 9704, 9511, 9319, 9126, 8933, 8739, 8545, + 8351, 8156, 7961, 7766, 7571, 7375, 7179, 6983, 6786, 6589, + 6392, 6195, 5997, 5799, 5601, 5403, 5205, 5006, 4807, 4609, + 4409, 4210, 4011, 3811, 3611, 3411, 3211, 3011, 2811, 2610, + 2410, 2209, 2009, 1808, 1607, 1406, 1206, 1005, 804, 603, + 402, 201, 0, -201, -402, -603, -804, -1005, -1206, -1406, + -1607, -1808, -2009, -2209, -2410, -2610, -2811, -3011, -3211, -3411, + -3611, -3811, -4011, -4210, -4409, -4609, -4807, -5006, -5205, -5403, + -5601, -5799, -5997, -6195, -6392, -6589, -6786, -6983, -7179, -7375, + -7571, -7766, -7961, -8156, -8351, -8545, -8739, -8933, -9126, -9319, + -9511, -9704, -9895, -10087, -10278, -10469, -10659, -10849, -11039, -11228, + -11416, -11605, -11792, -11980, -12167, -12353, -12539, -12725, -12910, -13094, + -13278, -13462, -13645, -13827, -14009, -14191, -14372, -14552, -14732, -14911, + -15090, -15268, -15446, -15623, -15799, -15975, -16151, -16325, -16499, -16673, + -16845, -17017, -17189, -17360, -17530, -17700, -17868, -18037, -18204, -18371, + -18537, -18703, -18867, -19031, -19195, -19357, -19519, -19680, -19841, -20000, + -20159, -20317, -20475, -20631, -20787, -20942, -21096, -21250, -21402, -21554, + -21705, -21855, -22005, -22153, -22301, -22448, -22594, -22739, -22884, -23027, + -23170, -23311, -23452, -23592, -23731, -23869, -24007, -24143, -24279, -24413, + -24547, -24680, -24811, -24942, -25072, -25201, -25329, -25456, -25582, -25707, + -25832, -25955, -26077, -26198, -26319, -26438, -26556, -26673, -26790, -26905, + -27019, -27132, -27245, -27356, -27466, -27575, -27683, -27790, -27896, -28001, + -28105, -28208, -28310, -28410, -28510, -28609, -28706, -28803, -28898, -28992, + -29085, -29177, -29268, -29358, -29447, -29534, -29621, -29706, -29791, -29874, + -29956, -30037, -30117, -30195, -30273, -30349, -30424, -30498, -30571, -30643, + -30714, -30783, -30852, -30919, -30985, -31050, -31113, -31176, -31237, -31297, + -31356, -31414, -31470, -31526, -31580, -31633, -31685, -31736, -31785, -31833, + -31880, -31926, -31971, -32014, -32057, -32098, -32137, -32176, -32213, -32250, + -32285, -32318, -32351, -32382, -32412, -32441, -32469, -32495, -32521, -32545, + -32567, -32589, -32609, -32628, -32646, -32663, -32678, -32692, -32705, -32717, + -32728, -32737, -32745, -32752, -32757, -32761, -32765, -32766, -32767, -32766, + -32765, -32761, -32757, -32752, -32745, -32737, -32728, -32717, -32705, -32692, + -32678, -32663, -32646, -32628, -32609, -32589, -32567, -32545, -32521, -32495, + -32469, -32441, -32412, -32382, -32351, -32318, -32285, -32250, -32213, -32176, + -32137, -32098, -32057, -32014, -31971, -31926, -31880, -31833, -31785, -31736, + -31685, -31633, -31580, -31526, -31470, -31414, -31356, -31297, -31237, -31176, + -31113, -31050, -30985, -30919, -30852, -30783, -30714, -30643, -30571, -30498, + -30424, -30349, -30273, -30195, -30117, -30037, -29956, -29874, -29791, -29706, + -29621, -29534, -29447, -29358, -29268, -29177, -29085, -28992, -28898, -28803, + -28706, -28609, -28510, -28410, -28310, -28208, -28105, -28001, -27896, -27790, + -27683, -27575, -27466, -27356, -27245, -27132, -27019, -26905, -26790, -26673, + -26556, -26438, -26319, -26198, -26077, -25955, -25832, -25707, -25582, -25456, + -25329, -25201, -25072, -24942, -24811, -24680, -24547, -24413, -24279, -24143, + -24007, -23869, -23731, -23592, -23452, -23311, -23170, -23027, -22884, -22739, + -22594, -22448, -22301, -22153, -22005, -21855, -21705, -21554, -21402, -21250, + -21096, -20942, -20787, -20631, -20475, -20317, -20159, -20000, -19841, -19680, + -19519, -19357, -19195, -19031, -18867, -18703, -18537, -18371, -18204, -18037, + -17868, -17700, -17530, -17360, -17189, -17017, -16845, -16673, -16499, -16325, + -16151, -15975, -15799, -15623, -15446, -15268, -15090, -14911, -14732, -14552, + -14372, -14191, -14009, -13827, -13645, -13462, -13278, -13094, -12910, -12725, + -12539, -12353, -12167, -11980, -11792, -11605, -11416, -11228, -11039, -10849, + -10659, -10469, -10278, -10087, -9895, -9704, -9511, -9319, -9126, -8933, + -8739, -8545, -8351, -8156, -7961, -7766, -7571, -7375, -7179, -6983, + -6786, -6589, -6392, -6195, -5997, -5799, -5601, -5403, -5205, -5006, + -4807, -4609, -4409, -4210, -4011, -3811, -3611, -3411, -3211, -3011, + -2811, -2610, -2410, -2209, -2009, -1808, -1607, -1406, -1206, -1005, + -804, -603, -402, -201, }; -const unsigned int toneVolumes[] = { 2, 4, 8, 12, 16 }; - #if defined(SDCARD) const char * audioFilenames[] = { "tada", @@ -541,6 +539,8 @@ int AudioQueue::mixWav(AudioContext &context, AudioBuffer *buffer, int volume, u } #endif +const unsigned int toneVolumes[] = { 2, 4, 8, 12, 16 }; + int AudioQueue::mixBeep(AudioContext &context, AudioBuffer *buffer, int volume, unsigned int fade) { AudioFragment & fragment = context.fragment; @@ -553,6 +553,7 @@ int AudioQueue::mixBeep(AudioContext &context, AudioBuffer *buffer, int volume, if (fragment.tone.freq) { context.state.tone.step = double(DIM(sineValues)*fragment.tone.freq) / AUDIO_SAMPLE_RATE; + context.state.tone.volume = (fragment.tone.freq * fragment.tone.freq * 32) / (110 * 110 * toneVolumes[2+volume]); if (fragment.tone.freqIncr) fragment.tone.freq += AUDIO_BUFFER_DURATION * fragment.tone.freqIncr; else @@ -577,7 +578,7 @@ int AudioQueue::mixBeep(AudioContext &context, AudioBuffer *buffer, int volume, } for (int i=0; idata[i], sample, fade); toneIdx += context.state.tone.step; if ((unsigned int)toneIdx >= DIM(sineValues)) diff --git a/radio/src/audio_arm.h b/radio/src/audio_arm.h index fadceeb59..6191da79f 100644 --- a/radio/src/audio_arm.h +++ b/radio/src/audio_arm.h @@ -106,7 +106,7 @@ class AudioContext { struct { double step; double idx; - double volume; + int volume; } tone; } state; From 7164375b7598b45c7e6449d6a85c36c699d8c956 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Mon, 17 Feb 2014 15:27:15 +0100 Subject: [PATCH 03/89] 2 harmonics added to the sine wave --- radio/src/audio_arm.cpp | 206 ++++++++++++++++++++-------------------- radio/util/sinus.py | 14 +++ 2 files changed, 117 insertions(+), 103 deletions(-) create mode 100644 radio/util/sinus.py diff --git a/radio/src/audio_arm.cpp b/radio/src/audio_arm.cpp index 45b53ba67..55c216afa 100644 --- a/radio/src/audio_arm.cpp +++ b/radio/src/audio_arm.cpp @@ -41,109 +41,109 @@ extern OS_MutexID audioMutex; const int16_t sineValues[] = { - 0, 201, 402, 603, 804, 1005, 1206, 1406, 1607, 1808, - 2009, 2209, 2410, 2610, 2811, 3011, 3211, 3411, 3611, 3811, - 4011, 4210, 4409, 4609, 4807, 5006, 5205, 5403, 5601, 5799, - 5997, 6195, 6392, 6589, 6786, 6983, 7179, 7375, 7571, 7766, - 7961, 8156, 8351, 8545, 8739, 8933, 9126, 9319, 9511, 9704, - 9895, 10087, 10278, 10469, 10659, 10849, 11039, 11228, 11416, 11605, - 11792, 11980, 12167, 12353, 12539, 12725, 12910, 13094, 13278, 13462, - 13645, 13827, 14009, 14191, 14372, 14552, 14732, 14911, 15090, 15268, - 15446, 15623, 15799, 15975, 16151, 16325, 16499, 16673, 16845, 17017, - 17189, 17360, 17530, 17700, 17868, 18037, 18204, 18371, 18537, 18703, - 18867, 19031, 19195, 19357, 19519, 19680, 19841, 20000, 20159, 20317, - 20475, 20631, 20787, 20942, 21096, 21250, 21402, 21554, 21705, 21855, - 22005, 22153, 22301, 22448, 22594, 22739, 22884, 23027, 23170, 23311, - 23452, 23592, 23731, 23869, 24007, 24143, 24279, 24413, 24547, 24680, - 24811, 24942, 25072, 25201, 25329, 25456, 25582, 25707, 25832, 25955, - 26077, 26198, 26319, 26438, 26556, 26673, 26790, 26905, 27019, 27132, - 27245, 27356, 27466, 27575, 27683, 27790, 27896, 28001, 28105, 28208, - 28310, 28410, 28510, 28609, 28706, 28803, 28898, 28992, 29085, 29177, - 29268, 29358, 29447, 29534, 29621, 29706, 29791, 29874, 29956, 30037, - 30117, 30195, 30273, 30349, 30424, 30498, 30571, 30643, 30714, 30783, - 30852, 30919, 30985, 31050, 31113, 31176, 31237, 31297, 31356, 31414, - 31470, 31526, 31580, 31633, 31685, 31736, 31785, 31833, 31880, 31926, - 31971, 32014, 32057, 32098, 32137, 32176, 32213, 32250, 32285, 32318, - 32351, 32382, 32412, 32441, 32469, 32495, 32521, 32545, 32567, 32589, - 32609, 32628, 32646, 32663, 32678, 32692, 32705, 32717, 32728, 32737, - 32745, 32752, 32757, 32761, 32765, 32766, 32767, 32766, 32765, 32761, - 32757, 32752, 32745, 32737, 32728, 32717, 32705, 32692, 32678, 32663, - 32646, 32628, 32609, 32589, 32567, 32545, 32521, 32495, 32469, 32441, - 32412, 32382, 32351, 32318, 32285, 32250, 32213, 32176, 32137, 32098, - 32057, 32014, 31971, 31926, 31880, 31833, 31785, 31736, 31685, 31633, - 31580, 31526, 31470, 31414, 31356, 31297, 31237, 31176, 31113, 31050, - 30985, 30919, 30852, 30783, 30714, 30643, 30571, 30498, 30424, 30349, - 30273, 30195, 30117, 30037, 29956, 29874, 29791, 29706, 29621, 29534, - 29447, 29358, 29268, 29177, 29085, 28992, 28898, 28803, 28706, 28609, - 28510, 28410, 28310, 28208, 28105, 28001, 27896, 27790, 27683, 27575, - 27466, 27356, 27245, 27132, 27019, 26905, 26790, 26673, 26556, 26438, - 26319, 26198, 26077, 25955, 25832, 25707, 25582, 25456, 25329, 25201, - 25072, 24942, 24811, 24680, 24547, 24413, 24279, 24143, 24007, 23869, - 23731, 23592, 23452, 23311, 23170, 23027, 22884, 22739, 22594, 22448, - 22301, 22153, 22005, 21855, 21705, 21554, 21402, 21250, 21096, 20942, - 20787, 20631, 20475, 20317, 20159, 20000, 19841, 19680, 19519, 19357, - 19195, 19031, 18867, 18703, 18537, 18371, 18204, 18037, 17868, 17700, - 17530, 17360, 17189, 17017, 16845, 16673, 16499, 16325, 16151, 15975, - 15799, 15623, 15446, 15268, 15090, 14911, 14732, 14552, 14372, 14191, - 14009, 13827, 13645, 13462, 13278, 13094, 12910, 12725, 12539, 12353, - 12167, 11980, 11792, 11605, 11416, 11228, 11039, 10849, 10659, 10469, - 10278, 10087, 9895, 9704, 9511, 9319, 9126, 8933, 8739, 8545, - 8351, 8156, 7961, 7766, 7571, 7375, 7179, 6983, 6786, 6589, - 6392, 6195, 5997, 5799, 5601, 5403, 5205, 5006, 4807, 4609, - 4409, 4210, 4011, 3811, 3611, 3411, 3211, 3011, 2811, 2610, - 2410, 2209, 2009, 1808, 1607, 1406, 1206, 1005, 804, 603, - 402, 201, 0, -201, -402, -603, -804, -1005, -1206, -1406, - -1607, -1808, -2009, -2209, -2410, -2610, -2811, -3011, -3211, -3411, - -3611, -3811, -4011, -4210, -4409, -4609, -4807, -5006, -5205, -5403, - -5601, -5799, -5997, -6195, -6392, -6589, -6786, -6983, -7179, -7375, - -7571, -7766, -7961, -8156, -8351, -8545, -8739, -8933, -9126, -9319, - -9511, -9704, -9895, -10087, -10278, -10469, -10659, -10849, -11039, -11228, - -11416, -11605, -11792, -11980, -12167, -12353, -12539, -12725, -12910, -13094, - -13278, -13462, -13645, -13827, -14009, -14191, -14372, -14552, -14732, -14911, - -15090, -15268, -15446, -15623, -15799, -15975, -16151, -16325, -16499, -16673, - -16845, -17017, -17189, -17360, -17530, -17700, -17868, -18037, -18204, -18371, - -18537, -18703, -18867, -19031, -19195, -19357, -19519, -19680, -19841, -20000, - -20159, -20317, -20475, -20631, -20787, -20942, -21096, -21250, -21402, -21554, - -21705, -21855, -22005, -22153, -22301, -22448, -22594, -22739, -22884, -23027, - -23170, -23311, -23452, -23592, -23731, -23869, -24007, -24143, -24279, -24413, - -24547, -24680, -24811, -24942, -25072, -25201, -25329, -25456, -25582, -25707, - -25832, -25955, -26077, -26198, -26319, -26438, -26556, -26673, -26790, -26905, - -27019, -27132, -27245, -27356, -27466, -27575, -27683, -27790, -27896, -28001, - -28105, -28208, -28310, -28410, -28510, -28609, -28706, -28803, -28898, -28992, - -29085, -29177, -29268, -29358, -29447, -29534, -29621, -29706, -29791, -29874, - -29956, -30037, -30117, -30195, -30273, -30349, -30424, -30498, -30571, -30643, - -30714, -30783, -30852, -30919, -30985, -31050, -31113, -31176, -31237, -31297, - -31356, -31414, -31470, -31526, -31580, -31633, -31685, -31736, -31785, -31833, - -31880, -31926, -31971, -32014, -32057, -32098, -32137, -32176, -32213, -32250, - -32285, -32318, -32351, -32382, -32412, -32441, -32469, -32495, -32521, -32545, - -32567, -32589, -32609, -32628, -32646, -32663, -32678, -32692, -32705, -32717, - -32728, -32737, -32745, -32752, -32757, -32761, -32765, -32766, -32767, -32766, - -32765, -32761, -32757, -32752, -32745, -32737, -32728, -32717, -32705, -32692, - -32678, -32663, -32646, -32628, -32609, -32589, -32567, -32545, -32521, -32495, - -32469, -32441, -32412, -32382, -32351, -32318, -32285, -32250, -32213, -32176, - -32137, -32098, -32057, -32014, -31971, -31926, -31880, -31833, -31785, -31736, - -31685, -31633, -31580, -31526, -31470, -31414, -31356, -31297, -31237, -31176, - -31113, -31050, -30985, -30919, -30852, -30783, -30714, -30643, -30571, -30498, - -30424, -30349, -30273, -30195, -30117, -30037, -29956, -29874, -29791, -29706, - -29621, -29534, -29447, -29358, -29268, -29177, -29085, -28992, -28898, -28803, - -28706, -28609, -28510, -28410, -28310, -28208, -28105, -28001, -27896, -27790, - -27683, -27575, -27466, -27356, -27245, -27132, -27019, -26905, -26790, -26673, - -26556, -26438, -26319, -26198, -26077, -25955, -25832, -25707, -25582, -25456, - -25329, -25201, -25072, -24942, -24811, -24680, -24547, -24413, -24279, -24143, - -24007, -23869, -23731, -23592, -23452, -23311, -23170, -23027, -22884, -22739, - -22594, -22448, -22301, -22153, -22005, -21855, -21705, -21554, -21402, -21250, - -21096, -20942, -20787, -20631, -20475, -20317, -20159, -20000, -19841, -19680, - -19519, -19357, -19195, -19031, -18867, -18703, -18537, -18371, -18204, -18037, - -17868, -17700, -17530, -17360, -17189, -17017, -16845, -16673, -16499, -16325, - -16151, -15975, -15799, -15623, -15446, -15268, -15090, -14911, -14732, -14552, - -14372, -14191, -14009, -13827, -13645, -13462, -13278, -13094, -12910, -12725, - -12539, -12353, -12167, -11980, -11792, -11605, -11416, -11228, -11039, -10849, - -10659, -10469, -10278, -10087, -9895, -9704, -9511, -9319, -9126, -8933, - -8739, -8545, -8351, -8156, -7961, -7766, -7571, -7375, -7179, -6983, - -6786, -6589, -6392, -6195, -5997, -5799, -5601, -5403, -5205, -5006, - -4807, -4609, -4409, -4210, -4011, -3811, -3611, -3411, -3211, -3011, - -2811, -2610, -2410, -2209, -2009, -1808, -1607, -1406, -1206, -1005, - -804, -603, -402, -201, + 0, 207, 414, 621, 829, 1036, 1243, 1450, 1657, 1864, + 2071, 2278, 2485, 2691, 2898, 3104, 3310, 3516, 3722, 3928, + 4133, 4338, 4543, 4748, 4953, 5157, 5361, 5565, 5769, 5972, + 6175, 6378, 6580, 6783, 6984, 7186, 7387, 7588, 7788, 7988, + 8188, 8387, 8586, 8785, 8983, 9180, 9378, 9574, 9771, 9967, + 10162, 10357, 10551, 10745, 10939, 11132, 11324, 11516, 11707, 11898, + 12088, 12278, 12467, 12656, 12844, 13031, 13218, 13404, 13589, 13774, + 13959, 14142, 14325, 14507, 14689, 14870, 15050, 15230, 15409, 15587, + 15764, 15941, 16117, 16293, 16467, 16641, 16814, 16986, 17158, 17329, + 17498, 17668, 17836, 18004, 18170, 18336, 18502, 18666, 18829, 18992, + 19154, 19315, 19475, 19634, 19793, 19950, 20107, 20262, 20417, 20571, + 20724, 20876, 21028, 21178, 21327, 21476, 21623, 21770, 21916, 22060, + 22204, 22347, 22489, 22630, 22770, 22909, 23047, 23184, 23320, 23455, + 23589, 23722, 23854, 23985, 24115, 24244, 24372, 24499, 24624, 24749, + 24873, 24996, 25118, 25239, 25358, 25477, 25595, 25711, 25827, 25941, + 26054, 26167, 26278, 26388, 26497, 26605, 26712, 26818, 26923, 27026, + 27129, 27231, 27331, 27430, 27529, 27626, 27722, 27817, 27910, 28003, + 28095, 28185, 28275, 28363, 28450, 28536, 28621, 28705, 28788, 28869, + 28950, 29029, 29107, 29184, 29260, 29335, 29409, 29481, 29553, 29623, + 29692, 29760, 29827, 29893, 29958, 30021, 30084, 30145, 30205, 30264, + 30322, 30378, 30434, 30488, 30542, 30594, 30645, 30694, 30743, 30791, + 30837, 30882, 30927, 30970, 31011, 31052, 31092, 31130, 31167, 31204, + 31239, 31272, 31305, 31337, 31367, 31397, 31425, 31452, 31478, 31502, + 31526, 31549, 31570, 31590, 31609, 31627, 31644, 31660, 31674, 31688, + 31700, 31711, 31721, 31730, 31738, 31744, 31750, 31754, 31757, 31760, + 31761, 31760, 31759, 31757, 31753, 31749, 31743, 31736, 31728, 31719, + 31709, 31698, 31685, 31672, 31657, 31641, 31624, 31606, 31587, 31567, + 31546, 31524, 31500, 31475, 31450, 31423, 31395, 31366, 31336, 31305, + 31273, 31239, 31205, 31169, 31133, 31095, 31056, 31016, 30975, 30933, + 30890, 30846, 30801, 30754, 30707, 30659, 30609, 30558, 30507, 30454, + 30400, 30345, 30289, 30232, 30174, 30115, 30055, 29994, 29932, 29868, + 29804, 29738, 29672, 29605, 29536, 29466, 29396, 29324, 29252, 29178, + 29103, 29027, 28951, 28873, 28794, 28714, 28633, 28552, 28469, 28385, + 28300, 28214, 28127, 28039, 27950, 27861, 27770, 27678, 27585, 27491, + 27396, 27301, 27204, 27106, 27007, 26908, 26807, 26705, 26603, 26499, + 26395, 26289, 26183, 26076, 25967, 25858, 25748, 25637, 25525, 25412, + 25298, 25183, 25067, 24951, 24833, 24715, 24595, 24475, 24354, 24232, + 24109, 23985, 23860, 23735, 23608, 23481, 23353, 23223, 23093, 22963, + 22831, 22698, 22565, 22431, 22296, 22160, 22023, 21885, 21747, 21608, + 21468, 21327, 21185, 21043, 20899, 20755, 20611, 20465, 20319, 20171, + 20023, 19875, 19725, 19575, 19424, 19272, 19120, 18967, 18813, 18658, + 18503, 18347, 18190, 18032, 17874, 17715, 17556, 17395, 17234, 17073, + 16910, 16747, 16584, 16420, 16255, 16089, 15923, 15756, 15589, 15421, + 15252, 15083, 14913, 14743, 14572, 14400, 14228, 14055, 13882, 13708, + 13534, 13359, 13183, 13007, 12831, 12654, 12476, 12298, 12120, 11941, + 11761, 11581, 11401, 11220, 11039, 10857, 10675, 10492, 10309, 10125, + 9941, 9757, 9572, 9387, 9202, 9016, 8830, 8643, 8456, 8269, + 8081, 7894, 7705, 7517, 7328, 7139, 6949, 6759, 6569, 6379, + 6189, 5998, 5807, 5615, 5424, 5232, 5040, 4848, 4656, 4463, + 4270, 4077, 3884, 3691, 3498, 3304, 3110, 2917, 2723, 2529, + 2334, 2140, 1946, 1752, 1557, 1362, 1168, 973, 779, 584, + 389, 194, 0, -194, -389, -584, -779, -973, -1168, -1362, + -1557, -1752, -1946, -2140, -2334, -2529, -2723, -2917, -3110, -3304, + -3498, -3691, -3884, -4077, -4270, -4463, -4656, -4848, -5040, -5232, + -5424, -5615, -5807, -5998, -6189, -6379, -6569, -6759, -6949, -7139, + -7328, -7517, -7705, -7894, -8081, -8269, -8456, -8643, -8830, -9016, + -9202, -9387, -9572, -9757, -9941, -10125, -10309, -10492, -10675, -10857, + -11039, -11220, -11401, -11581, -11761, -11941, -12120, -12298, -12476, -12654, + -12831, -13007, -13183, -13359, -13534, -13708, -13882, -14055, -14228, -14400, + -14572, -14743, -14913, -15083, -15252, -15421, -15589, -15756, -15923, -16089, + -16255, -16420, -16584, -16747, -16910, -17073, -17234, -17395, -17556, -17715, + -17874, -18032, -18190, -18347, -18503, -18658, -18813, -18967, -19120, -19272, + -19424, -19575, -19725, -19875, -20023, -20171, -20319, -20465, -20611, -20755, + -20899, -21043, -21185, -21327, -21468, -21608, -21747, -21885, -22023, -22160, + -22296, -22431, -22565, -22698, -22831, -22963, -23093, -23223, -23353, -23481, + -23608, -23735, -23860, -23985, -24109, -24232, -24354, -24475, -24595, -24715, + -24833, -24951, -25067, -25183, -25298, -25412, -25525, -25637, -25748, -25858, + -25967, -26076, -26183, -26289, -26395, -26499, -26603, -26705, -26807, -26908, + -27007, -27106, -27204, -27301, -27396, -27491, -27585, -27678, -27770, -27861, + -27950, -28039, -28127, -28214, -28300, -28385, -28469, -28552, -28633, -28714, + -28794, -28873, -28951, -29027, -29103, -29178, -29252, -29324, -29396, -29466, + -29536, -29605, -29672, -29738, -29804, -29868, -29932, -29994, -30055, -30115, + -30174, -30232, -30289, -30345, -30400, -30454, -30507, -30558, -30609, -30659, + -30707, -30754, -30801, -30846, -30890, -30933, -30975, -31016, -31056, -31095, + -31133, -31169, -31205, -31239, -31273, -31305, -31336, -31366, -31395, -31423, + -31450, -31475, -31500, -31524, -31546, -31567, -31587, -31606, -31624, -31641, + -31657, -31672, -31685, -31698, -31709, -31719, -31728, -31736, -31743, -31749, + -31753, -31757, -31759, -31760, -31761, -31760, -31757, -31754, -31750, -31744, + -31738, -31730, -31721, -31711, -31700, -31688, -31674, -31660, -31644, -31627, + -31609, -31590, -31570, -31549, -31526, -31502, -31478, -31452, -31425, -31397, + -31367, -31337, -31305, -31272, -31239, -31204, -31167, -31130, -31092, -31052, + -31011, -30970, -30927, -30882, -30837, -30791, -30743, -30694, -30645, -30594, + -30542, -30488, -30434, -30378, -30322, -30264, -30205, -30145, -30084, -30021, + -29958, -29893, -29827, -29760, -29692, -29623, -29553, -29481, -29409, -29335, + -29260, -29184, -29107, -29029, -28950, -28869, -28788, -28705, -28621, -28536, + -28450, -28363, -28275, -28185, -28095, -28003, -27910, -27817, -27722, -27626, + -27529, -27430, -27331, -27231, -27129, -27026, -26923, -26818, -26712, -26605, + -26497, -26388, -26278, -26167, -26054, -25941, -25827, -25711, -25595, -25477, + -25358, -25239, -25118, -24996, -24873, -24749, -24624, -24499, -24372, -24244, + -24115, -23985, -23854, -23722, -23589, -23455, -23320, -23184, -23047, -22909, + -22770, -22630, -22489, -22347, -22204, -22060, -21916, -21770, -21623, -21476, + -21327, -21178, -21028, -20876, -20724, -20571, -20417, -20262, -20107, -19950, + -19793, -19634, -19475, -19315, -19154, -18992, -18829, -18666, -18502, -18336, + -18170, -18004, -17836, -17668, -17498, -17329, -17158, -16986, -16814, -16641, + -16467, -16293, -16117, -15941, -15764, -15587, -15409, -15230, -15050, -14870, + -14689, -14507, -14325, -14142, -13959, -13774, -13589, -13404, -13218, -13031, + -12844, -12656, -12467, -12278, -12088, -11898, -11707, -11516, -11324, -11132, + -10939, -10745, -10551, -10357, -10162, -9967, -9771, -9574, -9378, -9180, + -8983, -8785, -8586, -8387, -8188, -7988, -7788, -7588, -7387, -7186, + -6984, -6783, -6580, -6378, -6175, -5972, -5769, -5565, -5361, -5157, + -4953, -4748, -4543, -4338, -4133, -3928, -3722, -3516, -3310, -3104, + -2898, -2691, -2485, -2278, -2071, -1864, -1657, -1450, -1243, -1036, + -829, -621, -414, -207, }; #if defined(SDCARD) diff --git a/radio/util/sinus.py b/radio/util/sinus.py new file mode 100644 index 000000000..0eeb135f1 --- /dev/null +++ b/radio/util/sinus.py @@ -0,0 +1,14 @@ +#!/bin/env python + +import math + +samples = 1024 +amplitudes = (63999, 1024, 512) + +for i in range(samples): + sample = 0.0 + for harmonic, amplitude in enumerate(amplitudes): + sample += math.sin(math.pi*2*i*(harmonic+1)/samples) * amplitude / 2 + print "%d," % int(sample), + if i % 10 == 9: + print From 967af60cbe3eb4198caeb93651f3d78a037ff31e Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Mon, 17 Feb 2014 23:26:12 +0100 Subject: [PATCH 04/89] Vario improvements --- companion/src/eeprominterface.h | 2 + .../src/firmwares/opentx/opentxeeprom.cpp | 2 + radio/src/audio_arm.cpp | 212 +++++++++--------- radio/src/audio_arm.h | 4 +- radio/src/gui/menu_general.cpp | 14 +- radio/src/maths.cpp | 79 ++++--- radio/src/myeeprom.h | 2 + radio/src/opentx.cpp | 6 +- radio/src/opentx.h | 4 + radio/src/telemetry/frsky_sport.cpp | 4 + radio/util/sinus.py | 4 +- 11 files changed, 182 insertions(+), 151 deletions(-) diff --git a/companion/src/eeprominterface.h b/companion/src/eeprominterface.h index 60f99b41a..7138836c1 100644 --- a/companion/src/eeprominterface.h +++ b/companion/src/eeprominterface.h @@ -462,6 +462,8 @@ class GeneralSettings { int beepVolume; int wavVolume; int varioVolume; + int varioPitch; + int varioRange; int backgroundVolume; unsigned int mavbaud; unsigned int switchUnlockStates; diff --git a/companion/src/firmwares/opentx/opentxeeprom.cpp b/companion/src/firmwares/opentx/opentxeeprom.cpp index 92b5c4b3e..ca70d75f1 100644 --- a/companion/src/firmwares/opentx/opentxeeprom.cpp +++ b/companion/src/firmwares/opentx/opentxeeprom.cpp @@ -2370,6 +2370,8 @@ Open9xGeneralDataNew::Open9xGeneralDataNew(GeneralSettings & generalData, BoardE internalField.Append(new SignedField<8>(generalData.beepVolume)); internalField.Append(new SignedField<8>(generalData.wavVolume)); internalField.Append(new SignedField<8>(generalData.varioVolume)); + internalField.Append(new SignedField<8>(generalData.varioPitch)); + internalField.Append(new SignedField<8>(generalData.varioRange)); internalField.Append(new SignedField<8>(generalData.backgroundVolume)); } if (IS_TARANIS(board) && version >= 216) { diff --git a/radio/src/audio_arm.cpp b/radio/src/audio_arm.cpp index 55c216afa..371f69ea7 100644 --- a/radio/src/audio_arm.cpp +++ b/radio/src/audio_arm.cpp @@ -41,109 +41,109 @@ extern OS_MutexID audioMutex; const int16_t sineValues[] = { - 0, 207, 414, 621, 829, 1036, 1243, 1450, 1657, 1864, - 2071, 2278, 2485, 2691, 2898, 3104, 3310, 3516, 3722, 3928, - 4133, 4338, 4543, 4748, 4953, 5157, 5361, 5565, 5769, 5972, - 6175, 6378, 6580, 6783, 6984, 7186, 7387, 7588, 7788, 7988, - 8188, 8387, 8586, 8785, 8983, 9180, 9378, 9574, 9771, 9967, - 10162, 10357, 10551, 10745, 10939, 11132, 11324, 11516, 11707, 11898, - 12088, 12278, 12467, 12656, 12844, 13031, 13218, 13404, 13589, 13774, - 13959, 14142, 14325, 14507, 14689, 14870, 15050, 15230, 15409, 15587, - 15764, 15941, 16117, 16293, 16467, 16641, 16814, 16986, 17158, 17329, - 17498, 17668, 17836, 18004, 18170, 18336, 18502, 18666, 18829, 18992, - 19154, 19315, 19475, 19634, 19793, 19950, 20107, 20262, 20417, 20571, - 20724, 20876, 21028, 21178, 21327, 21476, 21623, 21770, 21916, 22060, - 22204, 22347, 22489, 22630, 22770, 22909, 23047, 23184, 23320, 23455, - 23589, 23722, 23854, 23985, 24115, 24244, 24372, 24499, 24624, 24749, - 24873, 24996, 25118, 25239, 25358, 25477, 25595, 25711, 25827, 25941, - 26054, 26167, 26278, 26388, 26497, 26605, 26712, 26818, 26923, 27026, - 27129, 27231, 27331, 27430, 27529, 27626, 27722, 27817, 27910, 28003, - 28095, 28185, 28275, 28363, 28450, 28536, 28621, 28705, 28788, 28869, - 28950, 29029, 29107, 29184, 29260, 29335, 29409, 29481, 29553, 29623, - 29692, 29760, 29827, 29893, 29958, 30021, 30084, 30145, 30205, 30264, - 30322, 30378, 30434, 30488, 30542, 30594, 30645, 30694, 30743, 30791, - 30837, 30882, 30927, 30970, 31011, 31052, 31092, 31130, 31167, 31204, - 31239, 31272, 31305, 31337, 31367, 31397, 31425, 31452, 31478, 31502, - 31526, 31549, 31570, 31590, 31609, 31627, 31644, 31660, 31674, 31688, - 31700, 31711, 31721, 31730, 31738, 31744, 31750, 31754, 31757, 31760, - 31761, 31760, 31759, 31757, 31753, 31749, 31743, 31736, 31728, 31719, - 31709, 31698, 31685, 31672, 31657, 31641, 31624, 31606, 31587, 31567, - 31546, 31524, 31500, 31475, 31450, 31423, 31395, 31366, 31336, 31305, - 31273, 31239, 31205, 31169, 31133, 31095, 31056, 31016, 30975, 30933, - 30890, 30846, 30801, 30754, 30707, 30659, 30609, 30558, 30507, 30454, - 30400, 30345, 30289, 30232, 30174, 30115, 30055, 29994, 29932, 29868, - 29804, 29738, 29672, 29605, 29536, 29466, 29396, 29324, 29252, 29178, - 29103, 29027, 28951, 28873, 28794, 28714, 28633, 28552, 28469, 28385, - 28300, 28214, 28127, 28039, 27950, 27861, 27770, 27678, 27585, 27491, - 27396, 27301, 27204, 27106, 27007, 26908, 26807, 26705, 26603, 26499, - 26395, 26289, 26183, 26076, 25967, 25858, 25748, 25637, 25525, 25412, - 25298, 25183, 25067, 24951, 24833, 24715, 24595, 24475, 24354, 24232, - 24109, 23985, 23860, 23735, 23608, 23481, 23353, 23223, 23093, 22963, - 22831, 22698, 22565, 22431, 22296, 22160, 22023, 21885, 21747, 21608, - 21468, 21327, 21185, 21043, 20899, 20755, 20611, 20465, 20319, 20171, - 20023, 19875, 19725, 19575, 19424, 19272, 19120, 18967, 18813, 18658, - 18503, 18347, 18190, 18032, 17874, 17715, 17556, 17395, 17234, 17073, - 16910, 16747, 16584, 16420, 16255, 16089, 15923, 15756, 15589, 15421, - 15252, 15083, 14913, 14743, 14572, 14400, 14228, 14055, 13882, 13708, - 13534, 13359, 13183, 13007, 12831, 12654, 12476, 12298, 12120, 11941, - 11761, 11581, 11401, 11220, 11039, 10857, 10675, 10492, 10309, 10125, - 9941, 9757, 9572, 9387, 9202, 9016, 8830, 8643, 8456, 8269, - 8081, 7894, 7705, 7517, 7328, 7139, 6949, 6759, 6569, 6379, - 6189, 5998, 5807, 5615, 5424, 5232, 5040, 4848, 4656, 4463, - 4270, 4077, 3884, 3691, 3498, 3304, 3110, 2917, 2723, 2529, - 2334, 2140, 1946, 1752, 1557, 1362, 1168, 973, 779, 584, - 389, 194, 0, -194, -389, -584, -779, -973, -1168, -1362, - -1557, -1752, -1946, -2140, -2334, -2529, -2723, -2917, -3110, -3304, - -3498, -3691, -3884, -4077, -4270, -4463, -4656, -4848, -5040, -5232, - -5424, -5615, -5807, -5998, -6189, -6379, -6569, -6759, -6949, -7139, - -7328, -7517, -7705, -7894, -8081, -8269, -8456, -8643, -8830, -9016, - -9202, -9387, -9572, -9757, -9941, -10125, -10309, -10492, -10675, -10857, - -11039, -11220, -11401, -11581, -11761, -11941, -12120, -12298, -12476, -12654, - -12831, -13007, -13183, -13359, -13534, -13708, -13882, -14055, -14228, -14400, - -14572, -14743, -14913, -15083, -15252, -15421, -15589, -15756, -15923, -16089, - -16255, -16420, -16584, -16747, -16910, -17073, -17234, -17395, -17556, -17715, - -17874, -18032, -18190, -18347, -18503, -18658, -18813, -18967, -19120, -19272, - -19424, -19575, -19725, -19875, -20023, -20171, -20319, -20465, -20611, -20755, - -20899, -21043, -21185, -21327, -21468, -21608, -21747, -21885, -22023, -22160, - -22296, -22431, -22565, -22698, -22831, -22963, -23093, -23223, -23353, -23481, - -23608, -23735, -23860, -23985, -24109, -24232, -24354, -24475, -24595, -24715, - -24833, -24951, -25067, -25183, -25298, -25412, -25525, -25637, -25748, -25858, - -25967, -26076, -26183, -26289, -26395, -26499, -26603, -26705, -26807, -26908, - -27007, -27106, -27204, -27301, -27396, -27491, -27585, -27678, -27770, -27861, - -27950, -28039, -28127, -28214, -28300, -28385, -28469, -28552, -28633, -28714, - -28794, -28873, -28951, -29027, -29103, -29178, -29252, -29324, -29396, -29466, - -29536, -29605, -29672, -29738, -29804, -29868, -29932, -29994, -30055, -30115, - -30174, -30232, -30289, -30345, -30400, -30454, -30507, -30558, -30609, -30659, - -30707, -30754, -30801, -30846, -30890, -30933, -30975, -31016, -31056, -31095, - -31133, -31169, -31205, -31239, -31273, -31305, -31336, -31366, -31395, -31423, - -31450, -31475, -31500, -31524, -31546, -31567, -31587, -31606, -31624, -31641, - -31657, -31672, -31685, -31698, -31709, -31719, -31728, -31736, -31743, -31749, - -31753, -31757, -31759, -31760, -31761, -31760, -31757, -31754, -31750, -31744, - -31738, -31730, -31721, -31711, -31700, -31688, -31674, -31660, -31644, -31627, - -31609, -31590, -31570, -31549, -31526, -31502, -31478, -31452, -31425, -31397, - -31367, -31337, -31305, -31272, -31239, -31204, -31167, -31130, -31092, -31052, - -31011, -30970, -30927, -30882, -30837, -30791, -30743, -30694, -30645, -30594, - -30542, -30488, -30434, -30378, -30322, -30264, -30205, -30145, -30084, -30021, - -29958, -29893, -29827, -29760, -29692, -29623, -29553, -29481, -29409, -29335, - -29260, -29184, -29107, -29029, -28950, -28869, -28788, -28705, -28621, -28536, - -28450, -28363, -28275, -28185, -28095, -28003, -27910, -27817, -27722, -27626, - -27529, -27430, -27331, -27231, -27129, -27026, -26923, -26818, -26712, -26605, - -26497, -26388, -26278, -26167, -26054, -25941, -25827, -25711, -25595, -25477, - -25358, -25239, -25118, -24996, -24873, -24749, -24624, -24499, -24372, -24244, - -24115, -23985, -23854, -23722, -23589, -23455, -23320, -23184, -23047, -22909, - -22770, -22630, -22489, -22347, -22204, -22060, -21916, -21770, -21623, -21476, - -21327, -21178, -21028, -20876, -20724, -20571, -20417, -20262, -20107, -19950, - -19793, -19634, -19475, -19315, -19154, -18992, -18829, -18666, -18502, -18336, - -18170, -18004, -17836, -17668, -17498, -17329, -17158, -16986, -16814, -16641, - -16467, -16293, -16117, -15941, -15764, -15587, -15409, -15230, -15050, -14870, - -14689, -14507, -14325, -14142, -13959, -13774, -13589, -13404, -13218, -13031, - -12844, -12656, -12467, -12278, -12088, -11898, -11707, -11516, -11324, -11132, - -10939, -10745, -10551, -10357, -10162, -9967, -9771, -9574, -9378, -9180, - -8983, -8785, -8586, -8387, -8188, -7988, -7788, -7588, -7387, -7186, - -6984, -6783, -6580, -6378, -6175, -5972, -5769, -5565, -5361, -5157, - -4953, -4748, -4543, -4338, -4133, -3928, -3722, -3516, -3310, -3104, - -2898, -2691, -2485, -2278, -2071, -1864, -1657, -1450, -1243, -1036, - -829, -621, -414, -207, + 0, 218, 437, 655, 874, 1092, 1311, 1529, 1747, 1966, + 2184, 2401, 2619, 2837, 3054, 3271, 3488, 3705, 3921, 4138, + 4354, 4569, 4785, 5000, 5215, 5429, 5643, 5857, 6071, 6284, + 6496, 6709, 6920, 7132, 7343, 7553, 7763, 7973, 8182, 8390, + 8598, 8806, 9012, 9219, 9425, 9630, 9834, 10038, 10242, 10444, + 10646, 10848, 11049, 11249, 11448, 11647, 11845, 12042, 12238, 12434, + 12629, 12823, 13017, 13209, 13401, 13592, 13782, 13972, 14160, 14348, + 14535, 14721, 14906, 15090, 15273, 15456, 15637, 15818, 15997, 16176, + 16354, 16531, 16706, 16881, 17055, 17228, 17400, 17570, 17740, 17909, + 18077, 18243, 18409, 18574, 18737, 18899, 19061, 19221, 19380, 19538, + 19695, 19851, 20006, 20160, 20312, 20464, 20614, 20763, 20911, 21058, + 21204, 21348, 21491, 21634, 21775, 21914, 22053, 22191, 22327, 22462, + 22596, 22728, 22860, 22990, 23119, 23247, 23373, 23499, 23623, 23746, + 23867, 23988, 24107, 24225, 24342, 24457, 24571, 24684, 24796, 24906, + 25016, 25123, 25230, 25336, 25440, 25543, 25644, 25745, 25844, 25942, + 26039, 26134, 26228, 26321, 26412, 26503, 26592, 26680, 26766, 26852, + 26936, 27018, 27100, 27180, 27259, 27337, 27413, 27489, 27563, 27635, + 27707, 27777, 27846, 27914, 27980, 28046, 28110, 28173, 28234, 28295, + 28354, 28412, 28468, 28524, 28578, 28631, 28683, 28733, 28783, 28831, + 28878, 28924, 28968, 29011, 29054, 29095, 29134, 29173, 29210, 29247, + 29282, 29316, 29349, 29380, 29411, 29440, 29468, 29495, 29521, 29545, + 29569, 29591, 29613, 29633, 29652, 29670, 29686, 29702, 29717, 29730, + 29743, 29754, 29764, 29773, 29781, 29788, 29794, 29799, 29802, 29805, + 29806, 29807, 29806, 29805, 29802, 29799, 29794, 29788, 29781, 29773, + 29765, 29755, 29744, 29732, 29719, 29705, 29690, 29675, 29658, 29640, + 29621, 29601, 29580, 29559, 29536, 29512, 29488, 29462, 29435, 29408, + 29379, 29350, 29320, 29288, 29256, 29223, 29189, 29154, 29118, 29081, + 29044, 29005, 28966, 28925, 28884, 28842, 28799, 28755, 28710, 28664, + 28617, 28570, 28522, 28472, 28422, 28371, 28320, 28267, 28214, 28159, + 28104, 28048, 27991, 27934, 27875, 27816, 27756, 27695, 27633, 27570, + 27507, 27443, 27378, 27312, 27245, 27178, 27109, 27040, 26971, 26900, + 26829, 26756, 26683, 26610, 26535, 26460, 26384, 26307, 26229, 26151, + 26072, 25992, 25911, 25830, 25748, 25665, 25581, 25497, 25412, 25326, + 25239, 25152, 25064, 24975, 24885, 24795, 24704, 24612, 24520, 24427, + 24333, 24238, 24143, 24047, 23950, 23853, 23755, 23656, 23556, 23456, + 23355, 23254, 23151, 23048, 22945, 22840, 22735, 22630, 22523, 22416, + 22308, 22200, 22091, 21981, 21871, 21760, 21648, 21536, 21423, 21309, + 21194, 21079, 20964, 20848, 20731, 20613, 20495, 20376, 20257, 20137, + 20016, 19894, 19773, 19650, 19527, 19403, 19279, 19154, 19028, 18902, + 18775, 18647, 18519, 18391, 18262, 18132, 18001, 17870, 17739, 17607, + 17474, 17341, 17207, 17073, 16938, 16802, 16666, 16530, 16393, 16255, + 16117, 15978, 15839, 15699, 15559, 15418, 15277, 15135, 14992, 14850, + 14706, 14562, 14418, 14273, 14128, 13982, 13836, 13689, 13542, 13394, + 13246, 13097, 12948, 12799, 12649, 12498, 12347, 12196, 12044, 11892, + 11740, 11587, 11433, 11280, 11125, 10971, 10816, 10661, 10505, 10349, + 10192, 10036, 9878, 9721, 9563, 9405, 9246, 9087, 8928, 8768, + 8609, 8448, 8288, 8127, 7966, 7805, 7643, 7481, 7319, 7156, + 6994, 6831, 6667, 6504, 6340, 6176, 6012, 5847, 5683, 5518, + 5353, 5188, 5022, 4857, 4691, 4525, 4359, 4192, 4026, 3859, + 3692, 3526, 3358, 3191, 3024, 2857, 2689, 2521, 2354, 2186, + 2018, 1850, 1682, 1514, 1346, 1178, 1009, 841, 673, 505, + 336, 168, 0, -168, -336, -505, -673, -841, -1009, -1178, + -1346, -1514, -1682, -1850, -2018, -2186, -2354, -2521, -2689, -2857, + -3024, -3191, -3358, -3526, -3692, -3859, -4026, -4192, -4359, -4525, + -4691, -4857, -5022, -5188, -5353, -5518, -5683, -5847, -6012, -6176, + -6340, -6504, -6667, -6831, -6994, -7156, -7319, -7481, -7643, -7805, + -7966, -8127, -8288, -8448, -8609, -8768, -8928, -9087, -9246, -9405, + -9563, -9721, -9878, -10036, -10192, -10349, -10505, -10661, -10816, -10971, + -11125, -11280, -11433, -11587, -11740, -11892, -12044, -12196, -12347, -12498, + -12649, -12799, -12948, -13097, -13246, -13394, -13542, -13689, -13836, -13982, + -14128, -14273, -14418, -14562, -14706, -14850, -14992, -15135, -15277, -15418, + -15559, -15699, -15839, -15978, -16117, -16255, -16393, -16530, -16666, -16802, + -16938, -17073, -17207, -17341, -17474, -17607, -17739, -17870, -18001, -18132, + -18262, -18391, -18519, -18647, -18775, -18902, -19028, -19154, -19279, -19403, + -19527, -19650, -19773, -19894, -20016, -20137, -20257, -20376, -20495, -20613, + -20731, -20848, -20964, -21079, -21194, -21309, -21423, -21536, -21648, -21760, + -21871, -21981, -22091, -22200, -22308, -22416, -22523, -22630, -22735, -22840, + -22945, -23048, -23151, -23254, -23355, -23456, -23556, -23656, -23755, -23853, + -23950, -24047, -24143, -24238, -24333, -24427, -24520, -24612, -24704, -24795, + -24885, -24975, -25064, -25152, -25239, -25326, -25412, -25497, -25581, -25665, + -25748, -25830, -25911, -25992, -26072, -26151, -26229, -26307, -26384, -26460, + -26535, -26610, -26683, -26756, -26829, -26900, -26971, -27040, -27109, -27178, + -27245, -27312, -27378, -27443, -27507, -27570, -27633, -27695, -27756, -27816, + -27875, -27934, -27991, -28048, -28104, -28159, -28214, -28267, -28320, -28371, + -28422, -28472, -28522, -28570, -28617, -28664, -28710, -28755, -28799, -28842, + -28884, -28925, -28966, -29005, -29044, -29081, -29118, -29154, -29189, -29223, + -29256, -29288, -29320, -29350, -29379, -29408, -29435, -29462, -29488, -29512, + -29536, -29559, -29580, -29601, -29621, -29640, -29658, -29675, -29690, -29705, + -29719, -29732, -29744, -29755, -29765, -29773, -29781, -29788, -29794, -29799, + -29802, -29805, -29806, -29807, -29806, -29805, -29802, -29799, -29794, -29788, + -29781, -29773, -29764, -29754, -29743, -29730, -29717, -29702, -29686, -29670, + -29652, -29633, -29613, -29591, -29569, -29545, -29521, -29495, -29468, -29440, + -29411, -29380, -29349, -29316, -29282, -29247, -29210, -29173, -29134, -29095, + -29054, -29011, -28968, -28924, -28878, -28831, -28783, -28733, -28683, -28631, + -28578, -28524, -28468, -28412, -28354, -28295, -28234, -28173, -28110, -28046, + -27980, -27914, -27846, -27777, -27707, -27635, -27563, -27489, -27413, -27337, + -27259, -27180, -27100, -27018, -26936, -26852, -26766, -26680, -26592, -26503, + -26412, -26321, -26228, -26134, -26039, -25942, -25844, -25745, -25644, -25543, + -25440, -25336, -25230, -25123, -25016, -24906, -24796, -24684, -24571, -24457, + -24342, -24225, -24107, -23988, -23867, -23746, -23623, -23499, -23373, -23247, + -23119, -22990, -22860, -22728, -22596, -22462, -22327, -22191, -22053, -21914, + -21775, -21634, -21491, -21348, -21204, -21058, -20911, -20763, -20614, -20464, + -20312, -20160, -20006, -19851, -19695, -19538, -19380, -19221, -19061, -18899, + -18737, -18574, -18409, -18243, -18077, -17909, -17740, -17570, -17400, -17228, + -17055, -16881, -16706, -16531, -16354, -16176, -15997, -15818, -15637, -15456, + -15273, -15090, -14906, -14721, -14535, -14348, -14160, -13972, -13782, -13592, + -13401, -13209, -13017, -12823, -12629, -12434, -12238, -12042, -11845, -11647, + -11448, -11249, -11049, -10848, -10646, -10444, -10242, -10038, -9834, -9630, + -9425, -9219, -9012, -8806, -8598, -8390, -8182, -7973, -7763, -7553, + -7343, -7132, -6920, -6709, -6496, -6284, -6071, -5857, -5643, -5429, + -5215, -5000, -4785, -4569, -4354, -4138, -3921, -3705, -3488, -3271, + -3054, -2837, -2619, -2401, -2184, -1966, -1747, -1529, -1311, -1092, + -874, -655, -437, -218, }; #if defined(SDCARD) @@ -539,7 +539,7 @@ int AudioQueue::mixWav(AudioContext &context, AudioBuffer *buffer, int volume, u } #endif -const unsigned int toneVolumes[] = { 2, 4, 8, 12, 16 }; +const unsigned int toneVolumes[] = { 10, 8, 6, 4, 2 }; int AudioQueue::mixBeep(AudioContext &context, AudioBuffer *buffer, int volume, unsigned int fade) { @@ -553,7 +553,9 @@ int AudioQueue::mixBeep(AudioContext &context, AudioBuffer *buffer, int volume, if (fragment.tone.freq) { context.state.tone.step = double(DIM(sineValues)*fragment.tone.freq) / AUDIO_SAMPLE_RATE; - context.state.tone.volume = (fragment.tone.freq * fragment.tone.freq * 32) / (110 * 110 * toneVolumes[2+volume]); + context.state.tone.volume = toneVolumes[2+volume]; + if (fragment.tone.freq < 330) + context.state.tone.volume = (context.state.tone.volume * fragment.tone.freq * fragment.tone.freq) / (330 * 330); if (fragment.tone.freqIncr) fragment.tone.freq += AUDIO_BUFFER_DURATION * fragment.tone.freqIncr; else diff --git a/radio/src/audio_arm.h b/radio/src/audio_arm.h index 6191da79f..2738be4c2 100644 --- a/radio/src/audio_arm.h +++ b/radio/src/audio_arm.h @@ -47,7 +47,7 @@ #define AUDIO_BUFFER_SIZE (AUDIO_SAMPLE_RATE*AUDIO_BUFFER_DURATION/1000) #define AUDIO_BUFFER_COUNT (3) -#define BEEP_MIN_FREQ (110) +#define BEEP_MIN_FREQ (150) #define BEEP_DEFAULT_FREQ (2250) #define BEEP_KEY_UP_FREQ (BEEP_DEFAULT_FREQ+150) #define BEEP_KEY_DOWN_FREQ (BEEP_DEFAULT_FREQ-150) @@ -106,7 +106,7 @@ class AudioContext { struct { double step; double idx; - int volume; + float volume; } tone; } state; diff --git a/radio/src/gui/menu_general.cpp b/radio/src/gui/menu_general.cpp index 3b1ae8a7d..c66ae5bb2 100644 --- a/radio/src/gui/menu_general.cpp +++ b/radio/src/gui/menu_general.cpp @@ -150,6 +150,8 @@ enum menuGeneralSetupItems { IF_CPUARM(ITEM_SETUP_BEEP_VOLUME) IF_CPUARM(ITEM_SETUP_WAV_VOLUME) IF_CPUARM(ITEM_SETUP_VARIO_VOLUME) + IF_CPUARM(ITEM_SETUP_VARIO_PITCH) + IF_CPUARM(ITEM_SETUP_VARIO_RANGE) IF_CPUARM(ITEM_SETUP_BACKGROUND_VOLUME) ITEM_SETUP_BEEP_LENGTH, IF_AUDIO(ITEM_SETUP_SPEAKER_PITCH) @@ -211,7 +213,7 @@ void menuGeneralSetup(uint8_t event) } #endif - MENU(STR_MENURADIOSETUP, menuTabDiag, e_Setup, ITEM_SETUP_MAX+1, {0, IF_RTCLOCK(2) IF_RTCLOCK(2) IF_BATTGRAPH(1) LABEL(SOUND), IF_AUDIO(0) IF_BUZZER(0) IF_VOICE(0) IF_CPUARM(0) IF_CPUARM(0) IF_CPUARM(0) IF_CPUARM(0) 0, IF_AUDIO(0) IF_HAPTIC(LABEL(HAPTIC)) IF_HAPTIC(0) IF_HAPTIC(0) IF_HAPTIC(0) 0, LABEL(ALARMS), 0, CASE_PCBSKY9X(0) CASE_PCBSKY9X(0) 0, 0, 0, IF_ROTARY_ENCODERS(0) LABEL(BACKLIGHT), 0, 0, IF_CPUARM(0) CASE_PWM_BACKLIGHT(0) CASE_PWM_BACKLIGHT(0) 0, IF_SPLASH(0) IF_GPS(0) IF_GPS(0) IF_PXX(0) IF_CPUARM(0) IF_CPUARM(0) IF_FAI_CHOICE(0) 0, LABEL(TX_MODE), CASE_PCBTARANIS(0) 1/*to force edit mode*/}); + MENU(STR_MENURADIOSETUP, menuTabDiag, e_Setup, ITEM_SETUP_MAX+1, {0, IF_RTCLOCK(2) IF_RTCLOCK(2) IF_BATTGRAPH(1) LABEL(SOUND), IF_AUDIO(0) IF_BUZZER(0) IF_VOICE(0) IF_CPUARM(0) IF_CPUARM(0) IF_CPUARM(0) IF_CPUARM(0) IF_CPUARM(0) IF_CPUARM(0) 0, IF_AUDIO(0) IF_HAPTIC(LABEL(HAPTIC)) IF_HAPTIC(0) IF_HAPTIC(0) IF_HAPTIC(0) 0, LABEL(ALARMS), 0, CASE_PCBSKY9X(0) CASE_PCBSKY9X(0) 0, 0, 0, IF_ROTARY_ENCODERS(0) LABEL(BACKLIGHT), 0, 0, IF_CPUARM(0) CASE_PWM_BACKLIGHT(0) CASE_PWM_BACKLIGHT(0) 0, IF_SPLASH(0) IF_GPS(0) IF_GPS(0) IF_PXX(0) IF_CPUARM(0) IF_CPUARM(0) IF_FAI_CHOICE(0) 0, LABEL(TX_MODE), CASE_PCBTARANIS(0) 1/*to force edit mode*/}); uint8_t sub = m_posVert - 1; @@ -360,6 +362,16 @@ void menuGeneralSetup(uint8_t event) case ITEM_SETUP_VARIO_VOLUME: SLIDER_5POS(y, g_eeGeneral.varioVolume, STR_VARIO_VOLUME, event, attr); break; + case ITEM_SETUP_VARIO_PITCH: + lcd_putsLeft(y, "\001Vario Pitch"); + lcd_outdezAtt(RADIO_SETUP_2ND_COLUMN, y, VARIO_FREQUENCY_ZERO+(g_eeGeneral.varioPitch*10), attr|LEFT); + if (attr) CHECK_INCDEC_GENVAR(event, g_eeGeneral.varioPitch, -30, 30); + break; + case ITEM_SETUP_VARIO_RANGE: + lcd_putsLeft(y, "\001Vario Max"); + lcd_outdezAtt(RADIO_SETUP_2ND_COLUMN, y, VARIO_FREQUENCY_ZERO+(g_eeGeneral.varioPitch*10)+VARIO_FREQUENCY_RANGE+(g_eeGeneral.varioRange*10), attr|LEFT); + if (attr) CHECK_INCDEC_GENVAR(event, g_eeGeneral.varioRange, -30, 30); + break; case ITEM_SETUP_BACKGROUND_VOLUME: SLIDER_5POS(y, g_eeGeneral.backgroundVolume, STR_BG_VOLUME, event, attr); break; diff --git a/radio/src/maths.cpp b/radio/src/maths.cpp index 93330af1c..f729c4af2 100644 --- a/radio/src/maths.cpp +++ b/radio/src/maths.cpp @@ -123,7 +123,12 @@ void varioWakeup() if (isFunctionActive(FUNCTION_VARIO)) { #if defined(AUDIO) cli(); - int16_t verticalSpeed = frskyData.hub.varioSpeed; +#if 1 + #warning "Ele stick for vario tests" + int verticalSpeed = getValue(MIXSRC_Ele); +#else + int verticalSpeed = frskyData.hub.varioSpeed; +#endif sei(); #if defined(PCBSTD) @@ -135,60 +140,52 @@ void varioWakeup() verticalSpeed = (verticalSpeed * 10) / ((varioMax-varioCenterMax) / 100); if ((int16_t)(s_varioTmr-tmr10ms) < 0) { - uint8_t SoundVarioBeepTime = (1600 - verticalSpeed) / 100; - uint8_t SoundVarioBeepFreq = (verticalSpeed * 10 + 16000) >> 8; - s_varioTmr = tmr10ms + (SoundVarioBeepTime*2); - AUDIO_VARIO(SoundVarioBeepFreq, SoundVarioBeepTime); + uint8_t varioBeepFreq = (verticalSpeed * 10 + 16000) >> 8; + uint8_t varioBeepTime = (1600 - verticalSpeed) / 100; + s_varioTmr = tmr10ms + (varioBeepTime*2); + AUDIO_VARIO(varioBeepFreq, varioBeepTime); } } #else - int16_t varioCenterMax = (int16_t)g_model.frsky.varioCenterMax * 10 + 50; - if (verticalSpeed >= varioCenterMax) { - verticalSpeed = verticalSpeed - varioCenterMax; - int16_t varioMax = (10+(int16_t)g_model.frsky.varioMax) * 100; - if (verticalSpeed > varioMax) verticalSpeed = varioMax; - verticalSpeed = (verticalSpeed * 10) / ((varioMax-varioCenterMax) / 100); - } - else { - int16_t varioCenterMin = (int16_t)g_model.frsky.varioCenterMin * 10 - 50; - if (verticalSpeed <= varioCenterMin) { - verticalSpeed = verticalSpeed - varioCenterMin; - int16_t varioMin = (-10+(int16_t)g_model.frsky.varioMin) * 100; - if (verticalSpeed < varioMin) verticalSpeed = varioMin; - verticalSpeed = (verticalSpeed * 10) / ((varioCenterMin-varioMin) / 100); - } - else { - return; - } - } + int varioCenterMin = (int)g_model.frsky.varioCenterMin * 10 - 50; + int varioCenterMax = (int)g_model.frsky.varioCenterMax * 10 + 50; + int varioMax = (10+(int)g_model.frsky.varioMax) * 100; + int varioMin = (-10+(int)g_model.frsky.varioMin) * 100; - if (verticalSpeed < 0 || (int16_t)(s_varioTmr-tmr10ms) < 0) { + if (verticalSpeed > varioMax) + verticalSpeed = varioMax; + else if (verticalSpeed < varioMin) + verticalSpeed = varioMin; + + if ((int16_t)(s_varioTmr - tmr10ms) < 0) { #if defined(CPUARM) - int SoundVarioBeepTime; - int SoundVarioBeepFreq; - if (verticalSpeed > 0) { - SoundVarioBeepTime = min(5, 320 - (verticalSpeed >> 2)); - SoundVarioBeepFreq = 1000 + verticalSpeed; + int varioBeepFreq, varioBeepTime; + if (verticalSpeed > varioCenterMin) { + varioBeepFreq = VARIO_FREQUENCY_ZERO + (g_eeGeneral.varioPitch*10) + (((VARIO_FREQUENCY_RANGE+(g_eeGeneral.varioRange*10)) * verticalSpeed) / varioMax); + int period = VARIO_PERIOD_ZERO - ((VARIO_PERIOD_ZERO-VARIO_PERIOD_MAX) * verticalSpeed) / varioMax; + // TODO something exponential would be better + varioBeepTime = (verticalSpeed > varioCenterMax ? (period / 4) : (period / 2)); + s_varioTmr = tmr10ms + (period/10); } else { - SoundVarioBeepTime = 80; - SoundVarioBeepFreq = (verticalSpeed * 3 + 8000) >> 3; + varioBeepFreq = VARIO_FREQUENCY_ZERO + (g_eeGeneral.varioPitch*10) - (((VARIO_FREQUENCY_ZERO+(g_eeGeneral.varioPitch*10)-BEEP_MIN_FREQ) * verticalSpeed) / varioMin); + varioBeepTime = 80; // TODO 20 // continuous beep: we will enter again here before the tone ends + s_varioTmr = tmr10ms + 1; } - s_varioTmr = tmr10ms + (SoundVarioBeepTime/5); #else - uint8_t SoundVarioBeepTime; - uint8_t SoundVarioBeepFreq; + uint8_t varioBeepFreq, varioBeepTime; if (verticalSpeed > 0) { - SoundVarioBeepTime = (8000 - verticalSpeed * 5) / 100; - SoundVarioBeepFreq = (verticalSpeed * 4 + 8000) >> 7; + varioBeepFreq = (verticalSpeed * 4 + 8000) >> 7; + varioBeepTime = (8000 - verticalSpeed * 5) / 100; } else { - SoundVarioBeepTime = 20; - SoundVarioBeepFreq = (verticalSpeed * 3 + 8000) >> 7; + varioBeepFreq = (verticalSpeed * 3 + 8000) >> 7; + varioBeepTime = 20; } - s_varioTmr = tmr10ms + (SoundVarioBeepTime/2); + s_varioTmr = tmr10ms + (varioBeepTime/2); #endif - AUDIO_VARIO(SoundVarioBeepFreq, SoundVarioBeepTime); + + AUDIO_VARIO(varioBeepFreq, varioBeepTime); } #endif diff --git a/radio/src/myeeprom.h b/radio/src/myeeprom.h index fed0158f4..1b7ae1123 100644 --- a/radio/src/myeeprom.h +++ b/radio/src/myeeprom.h @@ -239,6 +239,8 @@ enum BeeperMode { int8_t beepVolume; \ int8_t wavVolume; \ int8_t varioVolume; \ + int8_t varioPitch; \ + int8_t varioRange; \ int8_t backgroundVolume; #endif diff --git a/radio/src/opentx.cpp b/radio/src/opentx.cpp index 320421007..33c2d82dd 100644 --- a/radio/src/opentx.cpp +++ b/radio/src/opentx.cpp @@ -4530,7 +4530,7 @@ void perMain() checkBacklight(); -#if defined(FRSKY) || defined(MAVLINK) +#if !defined(CPUARM) && (defined(FRSKY) || defined(MAVLINK)) telemetryWakeup(); #endif @@ -5188,6 +5188,10 @@ void mixerTask(void * pdata) CoLeaveMutexSection(mixerMutex); if (tick10ms) checkTrims(); +#if defined(FRSKY) || defined(MAVLINK) + telemetryWakeup(); +#endif + if (heartbeat == HEART_WDT_CHECK) { wdt_reset(); heartbeat = 0; diff --git a/radio/src/opentx.h b/radio/src/opentx.h index dcfed29a4..ce79231d2 100644 --- a/radio/src/opentx.h +++ b/radio/src/opentx.h @@ -1331,6 +1331,10 @@ enum FunctionsActive { #endif }; +#define VARIO_FREQUENCY_ZERO 700/*Hz*/ +#define VARIO_FREQUENCY_RANGE 1000/*Hz*/ +#define VARIO_PERIOD_ZERO 250/*ms*/ +#define VARIO_PERIOD_MAX 50/*ms*/ extern MASK_FUNC_TYPE activeFunctions; extern MASK_CFN_TYPE activeFnSwitches; diff --git a/radio/src/telemetry/frsky_sport.cpp b/radio/src/telemetry/frsky_sport.cpp index 1f0d53888..66eef97d6 100644 --- a/radio/src/telemetry/frsky_sport.cpp +++ b/radio/src/telemetry/frsky_sport.cpp @@ -655,7 +655,11 @@ void telemetryWakeup() #endif #if defined(VARIO) +#if 1 + #warning "test removed for vario tests" +#else if (TELEMETRY_STREAMING() && !IS_FAI_ENABLED()) +#endif varioWakeup(); #endif diff --git a/radio/util/sinus.py b/radio/util/sinus.py index 0eeb135f1..68c09456d 100644 --- a/radio/util/sinus.py +++ b/radio/util/sinus.py @@ -3,12 +3,14 @@ import math samples = 1024 -amplitudes = (63999, 1024, 512) +amplitudes = (60000, 4096, 1024) for i in range(samples): sample = 0.0 for harmonic, amplitude in enumerate(amplitudes): sample += math.sin(math.pi*2*i*(harmonic+1)/samples) * amplitude / 2 + if sample > 32767 or sample < -32768: + print "erreur" print "%d," % int(sample), if i % 10 == 9: print From 1767de646df2c2b4893a93874adbd0abafe83b7a Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Tue, 18 Feb 2014 11:33:02 +0100 Subject: [PATCH 05/89] Vario repeat parameter added --- radio/src/gui/menu_general.cpp | 12 +++++++++--- radio/src/maths.cpp | 9 ++++++--- radio/src/myeeprom.h | 1 + radio/src/opentx.h | 4 ++-- 4 files changed, 18 insertions(+), 8 deletions(-) diff --git a/radio/src/gui/menu_general.cpp b/radio/src/gui/menu_general.cpp index c66ae5bb2..14669926a 100644 --- a/radio/src/gui/menu_general.cpp +++ b/radio/src/gui/menu_general.cpp @@ -152,6 +152,7 @@ enum menuGeneralSetupItems { IF_CPUARM(ITEM_SETUP_VARIO_VOLUME) IF_CPUARM(ITEM_SETUP_VARIO_PITCH) IF_CPUARM(ITEM_SETUP_VARIO_RANGE) + IF_CPUARM(ITEM_SETUP_VARIO_REPEAT) IF_CPUARM(ITEM_SETUP_BACKGROUND_VOLUME) ITEM_SETUP_BEEP_LENGTH, IF_AUDIO(ITEM_SETUP_SPEAKER_PITCH) @@ -213,7 +214,7 @@ void menuGeneralSetup(uint8_t event) } #endif - MENU(STR_MENURADIOSETUP, menuTabDiag, e_Setup, ITEM_SETUP_MAX+1, {0, IF_RTCLOCK(2) IF_RTCLOCK(2) IF_BATTGRAPH(1) LABEL(SOUND), IF_AUDIO(0) IF_BUZZER(0) IF_VOICE(0) IF_CPUARM(0) IF_CPUARM(0) IF_CPUARM(0) IF_CPUARM(0) IF_CPUARM(0) IF_CPUARM(0) 0, IF_AUDIO(0) IF_HAPTIC(LABEL(HAPTIC)) IF_HAPTIC(0) IF_HAPTIC(0) IF_HAPTIC(0) 0, LABEL(ALARMS), 0, CASE_PCBSKY9X(0) CASE_PCBSKY9X(0) 0, 0, 0, IF_ROTARY_ENCODERS(0) LABEL(BACKLIGHT), 0, 0, IF_CPUARM(0) CASE_PWM_BACKLIGHT(0) CASE_PWM_BACKLIGHT(0) 0, IF_SPLASH(0) IF_GPS(0) IF_GPS(0) IF_PXX(0) IF_CPUARM(0) IF_CPUARM(0) IF_FAI_CHOICE(0) 0, LABEL(TX_MODE), CASE_PCBTARANIS(0) 1/*to force edit mode*/}); + MENU(STR_MENURADIOSETUP, menuTabDiag, e_Setup, ITEM_SETUP_MAX+1, {0, IF_RTCLOCK(2) IF_RTCLOCK(2) IF_BATTGRAPH(1) LABEL(SOUND), IF_AUDIO(0) IF_BUZZER(0) IF_VOICE(0) IF_CPUARM(0) IF_CPUARM(0) IF_CPUARM(0) IF_CPUARM(0) IF_CPUARM(0) IF_CPUARM(0) IF_CPUARM(0) 0, IF_AUDIO(0) IF_HAPTIC(LABEL(HAPTIC)) IF_HAPTIC(0) IF_HAPTIC(0) IF_HAPTIC(0) 0, LABEL(ALARMS), 0, CASE_PCBSKY9X(0) CASE_PCBSKY9X(0) 0, 0, 0, IF_ROTARY_ENCODERS(0) LABEL(BACKLIGHT), 0, 0, IF_CPUARM(0) CASE_PWM_BACKLIGHT(0) CASE_PWM_BACKLIGHT(0) 0, IF_SPLASH(0) IF_GPS(0) IF_GPS(0) IF_PXX(0) IF_CPUARM(0) IF_CPUARM(0) IF_FAI_CHOICE(0) 0, LABEL(TX_MODE), CASE_PCBTARANIS(0) 1/*to force edit mode*/}); uint8_t sub = m_posVert - 1; @@ -365,12 +366,17 @@ void menuGeneralSetup(uint8_t event) case ITEM_SETUP_VARIO_PITCH: lcd_putsLeft(y, "\001Vario Pitch"); lcd_outdezAtt(RADIO_SETUP_2ND_COLUMN, y, VARIO_FREQUENCY_ZERO+(g_eeGeneral.varioPitch*10), attr|LEFT); - if (attr) CHECK_INCDEC_GENVAR(event, g_eeGeneral.varioPitch, -30, 30); + if (attr) CHECK_INCDEC_GENVAR(event, g_eeGeneral.varioPitch, -40, 40); break; case ITEM_SETUP_VARIO_RANGE: lcd_putsLeft(y, "\001Vario Max"); lcd_outdezAtt(RADIO_SETUP_2ND_COLUMN, y, VARIO_FREQUENCY_ZERO+(g_eeGeneral.varioPitch*10)+VARIO_FREQUENCY_RANGE+(g_eeGeneral.varioRange*10), attr|LEFT); - if (attr) CHECK_INCDEC_GENVAR(event, g_eeGeneral.varioRange, -30, 30); + if (attr) CHECK_INCDEC_GENVAR(event, g_eeGeneral.varioRange, -80, 80); + break; + case ITEM_SETUP_VARIO_REPEAT: + lcd_putsLeft(y, "\001Vario Repeat"); + lcd_outdezAtt(RADIO_SETUP_2ND_COLUMN, y, VARIO_REPEAT_ZERO+(g_eeGeneral.varioRepeat*10), attr|LEFT); + if (attr) CHECK_INCDEC_GENVAR(event, g_eeGeneral.varioRepeat, -30, 120); break; case ITEM_SETUP_BACKGROUND_VOLUME: SLIDER_5POS(y, g_eeGeneral.backgroundVolume, STR_BG_VOLUME, event, attr); diff --git a/radio/src/maths.cpp b/radio/src/maths.cpp index f729c4af2..9cca70695 100644 --- a/radio/src/maths.cpp +++ b/radio/src/maths.cpp @@ -162,9 +162,12 @@ void varioWakeup() int varioBeepFreq, varioBeepTime; if (verticalSpeed > varioCenterMin) { varioBeepFreq = VARIO_FREQUENCY_ZERO + (g_eeGeneral.varioPitch*10) + (((VARIO_FREQUENCY_RANGE+(g_eeGeneral.varioRange*10)) * verticalSpeed) / varioMax); - int period = VARIO_PERIOD_ZERO - ((VARIO_PERIOD_ZERO-VARIO_PERIOD_MAX) * verticalSpeed) / varioMax; - // TODO something exponential would be better - varioBeepTime = (verticalSpeed > varioCenterMax ? (period / 4) : (period / 2)); + int period = VARIO_REPEAT_ZERO + (g_eeGeneral.varioRepeat*10); + period -= ((period-VARIO_REPEAT_MAX) * verticalSpeed) / varioMax; + if (verticalSpeed >= varioCenterMax || varioCenterMin == varioCenterMax) + varioBeepTime = period / 4; + else + varioBeepTime = period * (256 - ((verticalSpeed-varioCenterMin) * 172 / (varioCenterMax-varioCenterMin))) / 256; s_varioTmr = tmr10ms + (period/10); } else { diff --git a/radio/src/myeeprom.h b/radio/src/myeeprom.h index 1b7ae1123..8732a9f61 100644 --- a/radio/src/myeeprom.h +++ b/radio/src/myeeprom.h @@ -241,6 +241,7 @@ enum BeeperMode { int8_t varioVolume; \ int8_t varioPitch; \ int8_t varioRange; \ + int8_t varioRepeat; \ int8_t backgroundVolume; #endif diff --git a/radio/src/opentx.h b/radio/src/opentx.h index ce79231d2..b3bd33125 100644 --- a/radio/src/opentx.h +++ b/radio/src/opentx.h @@ -1333,8 +1333,8 @@ enum FunctionsActive { #define VARIO_FREQUENCY_ZERO 700/*Hz*/ #define VARIO_FREQUENCY_RANGE 1000/*Hz*/ -#define VARIO_PERIOD_ZERO 250/*ms*/ -#define VARIO_PERIOD_MAX 50/*ms*/ +#define VARIO_REPEAT_ZERO 500/*ms*/ +#define VARIO_REPEAT_MAX 50/*ms*/ extern MASK_FUNC_TYPE activeFunctions; extern MASK_CFN_TYPE activeFnSwitches; From ef51b2e6e87e2071e4d49bbb0d788d6df14319a7 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Tue, 18 Feb 2014 11:55:04 +0100 Subject: [PATCH 06/89] dTE added as a Vario source. Still not added the algorithms to take it into account, we don't have any dTE capable sensor yet --- radio/src/gui/menu_model.cpp | 5 +---- radio/src/myeeprom.h | 6 +++++- radio/src/translations/en.h | 6 +++--- 3 files changed, 9 insertions(+), 8 deletions(-) diff --git a/radio/src/gui/menu_model.cpp b/radio/src/gui/menu_model.cpp index 8d271aa56..5834962fd 100644 --- a/radio/src/gui/menu_model.cpp +++ b/radio/src/gui/menu_model.cpp @@ -5627,10 +5627,7 @@ void menuModelTelemetry(uint8_t event) } #else lcd_outdezAtt(TELEM_COL2, y, -10+g_model.frsky.varioMin, (m_posHorz<=0 ? attr : 0)|LEFT); - if (g_model.frsky.varioCenterMin == -16) - lcd_putsAtt(TELEM_COL2+4*FW-2, y, STR_OFF, m_posHorz==1 ? attr : 0); - else - lcd_outdezAtt(TELEM_COL2+7*FW-2, y, -5+g_model.frsky.varioCenterMin, ((m_posHorz<0 || m_posHorz==1) ? attr : 0)|PREC1); + lcd_outdezAtt(TELEM_COL2+7*FW-2, y, -5+g_model.frsky.varioCenterMin, ((m_posHorz<0 || m_posHorz==1) ? attr : 0)|PREC1); lcd_outdezAtt(TELEM_COL2+10*FW, y, 5+g_model.frsky.varioCenterMax, ((m_posHorz<0 || m_posHorz==2) ? attr : 0)|PREC1); lcd_outdezAtt(TELEM_COL2+13*FW+2, y, 10+g_model.frsky.varioMax, ((m_posHorz<0 || m_posHorz==3) ? attr : 0)); if (attr && (s_editMode>0 || p1valdiff)) { diff --git a/radio/src/myeeprom.h b/radio/src/myeeprom.h index 8732a9f61..e19ceddf9 100644 --- a/radio/src/myeeprom.h +++ b/radio/src/myeeprom.h @@ -998,7 +998,11 @@ enum VarioSource { VARIO_SOURCE_VARIO, VARIO_SOURCE_A1, VARIO_SOURCE_A2, - VARIO_SOURCE_LAST = VARIO_SOURCE_A2 +#if defined(FRSKY_SPORT) + VARIO_SOURCE_DTE, +#endif + VARIO_SOURCE_COUNT, + VARIO_SOURCE_LAST = VARIO_SOURCE_COUNT-1 }; #if defined(FRSKY_HUB) diff --git a/radio/src/translations/en.h b/radio/src/translations/en.h index 5d8b9dedc..1d1fcd108 100644 --- a/radio/src/translations/en.h +++ b/radio/src/translations/en.h @@ -297,11 +297,11 @@ #define LEN_VOLTSRC "\003" #define TR_VOLTSRC "---""A1\0""A2\0""FAS""Cel" -#define LEN_VARIOSRC "\005" +#define LEN_VARIOSRC "\004" #if defined(FRSKY_SPORT) - #define TR_VARIOSRC "Vario""A1\0 ""A2\0" + #define TR_VARIOSRC "VSpd""A1\0 ""A2\0 ""dTE\0" #else - #define TR_VARIOSRC "Alti\0""Alti+""Vario""A1\0 ""A2\0" + #define TR_VARIOSRC "Alt\0""Alt+""VSpd""A1\0 ""A2\0" #endif #define LEN_VSCREEN "\004" From 8c5798443ac1578ec80e948729fae7370cb5e233 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Tue, 18 Feb 2014 15:01:54 +0100 Subject: [PATCH 07/89] Vario experiments around tone/silence ratio. Now (100% / 75%-50% linear / 25%) --- radio/src/maths.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/radio/src/maths.cpp b/radio/src/maths.cpp index 9cca70695..5874cece7 100644 --- a/radio/src/maths.cpp +++ b/radio/src/maths.cpp @@ -167,7 +167,7 @@ void varioWakeup() if (verticalSpeed >= varioCenterMax || varioCenterMin == varioCenterMax) varioBeepTime = period / 4; else - varioBeepTime = period * (256 - ((verticalSpeed-varioCenterMin) * 172 / (varioCenterMax-varioCenterMin))) / 256; + varioBeepTime = period * (172 - ((verticalSpeed-varioCenterMin) * 64 / (varioCenterMax-varioCenterMin))) / 256; s_varioTmr = tmr10ms + (period/10); } else { From ec6d1c1212c860a9995d2cb8d169a917e88522f8 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Tue, 18 Feb 2014 15:04:20 +0100 Subject: [PATCH 08/89] Companion import/export for new vario parameters --- companion/src/eeprominterface.h | 1 + companion/src/firmwares/opentx/opentxeeprom.cpp | 7 +++++-- 2 files changed, 6 insertions(+), 2 deletions(-) diff --git a/companion/src/eeprominterface.h b/companion/src/eeprominterface.h index 7138836c1..13b68339e 100644 --- a/companion/src/eeprominterface.h +++ b/companion/src/eeprominterface.h @@ -464,6 +464,7 @@ class GeneralSettings { int varioVolume; int varioPitch; int varioRange; + int varioRepeat; int backgroundVolume; unsigned int mavbaud; unsigned int switchUnlockStates; diff --git a/companion/src/firmwares/opentx/opentxeeprom.cpp b/companion/src/firmwares/opentx/opentxeeprom.cpp index ca70d75f1..3e740b630 100644 --- a/companion/src/firmwares/opentx/opentxeeprom.cpp +++ b/companion/src/firmwares/opentx/opentxeeprom.cpp @@ -2370,8 +2370,11 @@ Open9xGeneralDataNew::Open9xGeneralDataNew(GeneralSettings & generalData, BoardE internalField.Append(new SignedField<8>(generalData.beepVolume)); internalField.Append(new SignedField<8>(generalData.wavVolume)); internalField.Append(new SignedField<8>(generalData.varioVolume)); - internalField.Append(new SignedField<8>(generalData.varioPitch)); - internalField.Append(new SignedField<8>(generalData.varioRange)); + if (version >= 216) { + internalField.Append(new SignedField<8>(generalData.varioPitch)); + internalField.Append(new SignedField<8>(generalData.varioRange)); + internalField.Append(new SignedField<8>(generalData.varioRepeat)); + } internalField.Append(new SignedField<8>(generalData.backgroundVolume)); } if (IS_TARANIS(board) && version >= 216) { From 0157eebf7cb801a409e3bd9f0db7a7026cd9d39b Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Tue, 18 Feb 2014 16:08:42 +0100 Subject: [PATCH 09/89] Vario: allows a refresh of tones frequency / duration every 10ms --- companion/src/modeledit/customfunctions.cpp | 3 +- radio/src/audio_arm.cpp | 192 ++++++++++---------- radio/src/audio_arm.h | 21 ++- radio/src/maths.cpp | 6 +- 4 files changed, 116 insertions(+), 106 deletions(-) diff --git a/companion/src/modeledit/customfunctions.cpp b/companion/src/modeledit/customfunctions.cpp index 49f7630e8..2422477bc 100644 --- a/companion/src/modeledit/customfunctions.cpp +++ b/companion/src/modeledit/customfunctions.cpp @@ -255,7 +255,8 @@ void CustomFunctionsPanel::playMusic() clickObject->play(); playBT[index]->setObjectName(QString("stop_%1").arg(index)); playBT[index]->setIcon(CompanionIcon("stop.png")); - } else { + } + else { clickObject->stop(); clickObject->clear(); playBT[index]->setObjectName(QString("play_%1").arg(index)); diff --git a/radio/src/audio_arm.cpp b/radio/src/audio_arm.cpp index 371f69ea7..f9a9bc38d 100644 --- a/radio/src/audio_arm.cpp +++ b/radio/src/audio_arm.cpp @@ -529,7 +529,7 @@ int AudioQueue::mixWav(AudioContext &context, AudioBuffer *buffer, int volume, u } } - fragment.clear(); + context.clear(); return -result; } #else @@ -540,31 +540,42 @@ int AudioQueue::mixWav(AudioContext &context, AudioBuffer *buffer, int volume, u #endif const unsigned int toneVolumes[] = { 10, 8, 6, 4, 2 }; +inline float evalVolumeRatio(int freq, int volume) +{ + float result = toneVolumes[2+volume]; + if (freq < 330) { + result = (result * freq * freq) / (330 * 330); + } + return result; +} -int AudioQueue::mixBeep(AudioContext &context, AudioBuffer *buffer, int volume, unsigned int fade) +int AudioQueue::mixTone(AudioContext &context, AudioBuffer *buffer, int volume, unsigned int fade) { AudioFragment & fragment = context.fragment; int duration = 0; int result = 0; - if (fragment.tone.duration > 0) { + int remainingDuration = fragment.tone.duration - context.state.tone.duration; + if (remainingDuration > 0) { int points; double toneIdx = context.state.tone.idx; - if (fragment.tone.freq) { + if (fragment.tone.freq != context.state.tone.freq) { + context.state.tone.freq = fragment.tone.freq; context.state.tone.step = double(DIM(sineValues)*fragment.tone.freq) / AUDIO_SAMPLE_RATE; - context.state.tone.volume = toneVolumes[2+volume]; - if (fragment.tone.freq < 330) - context.state.tone.volume = (context.state.tone.volume * fragment.tone.freq * fragment.tone.freq) / (330 * 330); - if (fragment.tone.freqIncr) - fragment.tone.freq += AUDIO_BUFFER_DURATION * fragment.tone.freqIncr; - else - fragment.tone.freq = 0; + context.state.tone.volume = evalVolumeRatio(fragment.tone.freq, volume); } - if (fragment.tone.duration <= AUDIO_BUFFER_DURATION) { - duration = fragment.tone.duration; - fragment.tone.duration = 0; + if (fragment.tone.freqIncr) { + fragment.tone.freq += AUDIO_BUFFER_DURATION * fragment.tone.freqIncr; + } + + if (remainingDuration > AUDIO_BUFFER_DURATION) { + duration = AUDIO_BUFFER_DURATION; + points = AUDIO_BUFFER_SIZE; + } + else { + duration = remainingDuration; points = (duration * AUDIO_BUFFER_SIZE) / AUDIO_BUFFER_DURATION; unsigned int end = toneIdx + (context.state.tone.step * points); if (end > DIM(sineValues)) @@ -573,11 +584,6 @@ int AudioQueue::mixBeep(AudioContext &context, AudioBuffer *buffer, int volume, end = DIM(sineValues); points = (double(end) - toneIdx) / context.state.tone.step; } - else { - duration = AUDIO_BUFFER_DURATION; - fragment.tone.duration -= AUDIO_BUFFER_DURATION; - points = AUDIO_BUFFER_SIZE; - } for (int i=0; i 0) { + if (remainingDuration > AUDIO_BUFFER_DURATION) { + context.state.tone.duration += AUDIO_BUFFER_DURATION; context.state.tone.idx = toneIdx; return AUDIO_BUFFER_SIZE; } else { + context.state.tone.duration = 32000; // once the tone is finished, it's not possible to update its frequency and duration context.state.tone.idx = 0; } } - if (fragment.tone.pause > 0) { + remainingDuration = fragment.tone.pause - context.state.tone.pause; + if (remainingDuration > 0) { result = AUDIO_BUFFER_SIZE; - fragment.tone.pause -= min(AUDIO_BUFFER_DURATION-duration, fragment.tone.pause); - if (fragment.tone.pause > 0) - return AUDIO_BUFFER_SIZE; + context.state.tone.pause += min(AUDIO_BUFFER_DURATION-duration, fragment.tone.pause); + if (fragment.tone.pause > context.state.tone.pause) + return result; } - fragment.clear(); + context.clear(); return result; } @@ -613,7 +622,7 @@ int AudioQueue::mixAudioContext(AudioContext &context, AudioBuffer *buffer, int AudioFragment & fragment = context.fragment; if (fragment.type == FRAGMENT_TONE) { - result = mixBeep(context, buffer, beepVolume, fade); + result = mixTone(context, buffer, beepVolume, fade); } else if (fragment.type == FRAGMENT_FILE) { result = mixWav(context, buffer, wavVolume, fade); @@ -693,7 +702,7 @@ inline unsigned int getToneLength(uint16_t len) void AudioQueue::pause(uint16_t len) { - play(0, 0, len); + playTone(0, 0, len); } bool AudioQueue::isPlaying(uint8_t id) @@ -711,7 +720,7 @@ bool AudioQueue::isPlaying(uint8_t id) return false; } -void AudioQueue::play(uint16_t freq, uint16_t len, uint16_t pause, uint8_t flags, int8_t freqIncr) +void AudioQueue::playTone(uint16_t freq, uint16_t len, uint16_t pause, uint8_t flags, int8_t freqIncr) { CoEnterMutexSection(audioMutex); @@ -720,7 +729,6 @@ void AudioQueue::play(uint16_t freq, uint16_t len, uint16_t pause, uint8_t flags if (flags & PLAY_BACKGROUND) { AudioFragment & fragment = backgroundContext.fragment; - backgroundContext.clear(); fragment.type = FRAGMENT_TONE; fragment.tone.freq = freq; fragment.tone.duration = len; @@ -833,7 +841,7 @@ void AudioQueue::stopSD() { sdAvailableSystemAudioFiles = 0; reset(); - play(0, 0, 100, PLAY_NOW); // insert a 100ms pause + playTone(0, 0, 100, PLAY_NOW); // insert a 100ms pause } #endif @@ -875,23 +883,23 @@ void audioEvent(uint8_t e, uint16_t f) switch (e) { // inactivity timer alert case AU_INACTIVITY: - audioQueue.play(2250, 80, 20, PLAY_REPEAT(2)); + audioQueue.playTone(2250, 80, 20, PLAY_REPEAT(2)); break; // low battery in tx case AU_TX_BATTERY_LOW: - audioQueue.play(1950, 160, 20, PLAY_REPEAT(2), 1); - audioQueue.play(2550, 160, 20, PLAY_REPEAT(2), -1); + audioQueue.playTone(1950, 160, 20, PLAY_REPEAT(2), 1); + audioQueue.playTone(2550, 160, 20, PLAY_REPEAT(2), -1); break; #if defined(PCBSKY9X) case AU_TX_MAH_HIGH: // TODO Rob something better here? - audioQueue.play(1950, 160, 20, PLAY_REPEAT(2), 1); - audioQueue.play(2550, 160, 20, PLAY_REPEAT(2), -1); + audioQueue.playTone(1950, 160, 20, PLAY_REPEAT(2), 1); + audioQueue.playTone(2550, 160, 20, PLAY_REPEAT(2), -1); break; case AU_TX_TEMP_HIGH: // TODO Rob something better here? - audioQueue.play(1950, 160, 20, PLAY_REPEAT(2), 1); - audioQueue.play(2550, 160, 20, PLAY_REPEAT(2), -1); + audioQueue.playTone(1950, 160, 20, PLAY_REPEAT(2), 1); + audioQueue.playTone(2550, 160, 20, PLAY_REPEAT(2), -1); break; #endif #if defined(VOICE) @@ -899,43 +907,43 @@ void audioEvent(uint8_t e, uint16_t f) case AU_SWITCH_ALERT: #endif case AU_ERROR: - audioQueue.play(BEEP_DEFAULT_FREQ, 200, 20, PLAY_NOW); + audioQueue.playTone(BEEP_DEFAULT_FREQ, 200, 20, PLAY_NOW); break; // keypad up (seems to be used when going left/right through system menu options. 0-100 scales etc) case AU_KEYPAD_UP: - audioQueue.play(BEEP_KEY_UP_FREQ, 80, 20, PLAY_NOW); + audioQueue.playTone(BEEP_KEY_UP_FREQ, 80, 20, PLAY_NOW); break; // keypad down (seems to be used when going left/right through system menu options. 0-100 scales etc) case AU_KEYPAD_DOWN: - audioQueue.play(BEEP_KEY_DOWN_FREQ, 80, 20, PLAY_NOW); + audioQueue.playTone(BEEP_KEY_DOWN_FREQ, 80, 20, PLAY_NOW); break; // menu display (also used by a few generic beeps) case AU_MENUS: - audioQueue.play(BEEP_DEFAULT_FREQ, 80, 20, PLAY_NOW); + audioQueue.playTone(BEEP_DEFAULT_FREQ, 80, 20, PLAY_NOW); break; // trim move case AU_TRIM_MOVE: - audioQueue.play(f, 40, 20, PLAY_NOW); + audioQueue.playTone(f, 40, 20, PLAY_NOW); break; // trim center case AU_TRIM_MIDDLE: - audioQueue.play(f, 80, 20, PLAY_NOW); + audioQueue.playTone(f, 80, 20, PLAY_NOW); break; // trim center case AU_TRIM_END: - audioQueue.play(f, 80, 20, PLAY_NOW); + audioQueue.playTone(f, 80, 20, PLAY_NOW); break; // warning one case AU_WARNING1: - audioQueue.play(BEEP_DEFAULT_FREQ, 80, 20, PLAY_NOW); + audioQueue.playTone(BEEP_DEFAULT_FREQ, 80, 20, PLAY_NOW); break; // warning two case AU_WARNING2: - audioQueue.play(BEEP_DEFAULT_FREQ, 160, 20, PLAY_NOW); + audioQueue.playTone(BEEP_DEFAULT_FREQ, 160, 20, PLAY_NOW); break; // warning three case AU_WARNING3: - audioQueue.play(BEEP_DEFAULT_FREQ, 200, 20, PLAY_NOW); + audioQueue.playTone(BEEP_DEFAULT_FREQ, 200, 20, PLAY_NOW); break; // pot/stick center case AU_STICK1_MIDDLE: @@ -950,120 +958,120 @@ void audioEvent(uint8_t e, uint16_t f) #else case AU_POT3_MIDDLE: #endif - audioQueue.play(BEEP_DEFAULT_FREQ+1500, 80, 20, PLAY_NOW); + audioQueue.playTone(BEEP_DEFAULT_FREQ+1500, 80, 20, PLAY_NOW); break; // mix warning 1 case AU_MIX_WARNING_1: - audioQueue.play(BEEP_DEFAULT_FREQ+1440, 48, 32); + audioQueue.playTone(BEEP_DEFAULT_FREQ+1440, 48, 32); break; // mix warning 2 case AU_MIX_WARNING_2: - audioQueue.play(BEEP_DEFAULT_FREQ+1560, 48, 32, PLAY_REPEAT(1)); + audioQueue.playTone(BEEP_DEFAULT_FREQ+1560, 48, 32, PLAY_REPEAT(1)); break; // mix warning 3 case AU_MIX_WARNING_3: - audioQueue.play(BEEP_DEFAULT_FREQ+1680, 48, 32, PLAY_REPEAT(2)); + audioQueue.playTone(BEEP_DEFAULT_FREQ+1680, 48, 32, PLAY_REPEAT(2)); break; // timer == 0 case AU_TIMER_00: - audioQueue.play(BEEP_DEFAULT_FREQ+150, 300, 20, PLAY_NOW); + audioQueue.playTone(BEEP_DEFAULT_FREQ+150, 300, 20, PLAY_NOW); break; // timer <= 10 seconds left case AU_TIMER_LT10: - audioQueue.play(BEEP_DEFAULT_FREQ+150, 120, 20, PLAY_NOW); + audioQueue.playTone(BEEP_DEFAULT_FREQ+150, 120, 20, PLAY_NOW); break; // timer 20 seconds left case AU_TIMER_20: - audioQueue.play(BEEP_DEFAULT_FREQ+150, 120, 20, PLAY_REPEAT(1)|PLAY_NOW); + audioQueue.playTone(BEEP_DEFAULT_FREQ+150, 120, 20, PLAY_REPEAT(1)|PLAY_NOW); break; // timer 30 seconds left case AU_TIMER_30: - audioQueue.play(BEEP_DEFAULT_FREQ+150, 120, 20, PLAY_REPEAT(2)|PLAY_NOW); + audioQueue.playTone(BEEP_DEFAULT_FREQ+150, 120, 20, PLAY_REPEAT(2)|PLAY_NOW); break; #if defined(PCBTARANIS) case AU_A1_ORANGE: - audioQueue.play(BEEP_DEFAULT_FREQ+600, 200, 20, PLAY_NOW); + audioQueue.playTone(BEEP_DEFAULT_FREQ+600, 200, 20, PLAY_NOW); break; case AU_A1_RED: - audioQueue.play(BEEP_DEFAULT_FREQ+600, 200, 20, PLAY_REPEAT(1)|PLAY_NOW); + audioQueue.playTone(BEEP_DEFAULT_FREQ+600, 200, 20, PLAY_REPEAT(1)|PLAY_NOW); break; case AU_A2_ORANGE: - audioQueue.play(BEEP_DEFAULT_FREQ+1500, 200, 20, PLAY_NOW); + audioQueue.playTone(BEEP_DEFAULT_FREQ+1500, 200, 20, PLAY_NOW); break; case AU_A2_RED: - audioQueue.play(BEEP_DEFAULT_FREQ+1500, 200, 20, PLAY_REPEAT(1)|PLAY_NOW); + audioQueue.playTone(BEEP_DEFAULT_FREQ+1500, 200, 20, PLAY_REPEAT(1)|PLAY_NOW); break; case AU_RSSI_ORANGE: - audioQueue.play(BEEP_DEFAULT_FREQ+1500, 800, 20, PLAY_NOW); + audioQueue.playTone(BEEP_DEFAULT_FREQ+1500, 800, 20, PLAY_NOW); break; case AU_RSSI_RED: - audioQueue.play(BEEP_DEFAULT_FREQ+1800, 800, 20, PLAY_REPEAT(1)|PLAY_NOW); + audioQueue.playTone(BEEP_DEFAULT_FREQ+1800, 800, 20, PLAY_REPEAT(1)|PLAY_NOW); break; case AU_SWR_RED: - audioQueue.play(450, 160, 40, PLAY_REPEAT(2), 1); + audioQueue.playTone(450, 160, 40, PLAY_REPEAT(2), 1); break; #endif case AU_FRSKY_BEEP1: - audioQueue.play(BEEP_DEFAULT_FREQ, 60, 20); + audioQueue.playTone(BEEP_DEFAULT_FREQ, 60, 20); break; case AU_FRSKY_BEEP2: - audioQueue.play(BEEP_DEFAULT_FREQ, 120, 20); + audioQueue.playTone(BEEP_DEFAULT_FREQ, 120, 20); break; case AU_FRSKY_BEEP3: - audioQueue.play(BEEP_DEFAULT_FREQ, 200, 20); + audioQueue.playTone(BEEP_DEFAULT_FREQ, 200, 20); break; case AU_FRSKY_WARN1: - audioQueue.play(BEEP_DEFAULT_FREQ+600, 120, 40, PLAY_REPEAT(2)); + audioQueue.playTone(BEEP_DEFAULT_FREQ+600, 120, 40, PLAY_REPEAT(2)); break; case AU_FRSKY_WARN2: - audioQueue.play(BEEP_DEFAULT_FREQ+900, 120, 40, PLAY_REPEAT(2)); + audioQueue.playTone(BEEP_DEFAULT_FREQ+900, 120, 40, PLAY_REPEAT(2)); break; case AU_FRSKY_CHEEP: - audioQueue.play(BEEP_DEFAULT_FREQ+900, 80, 20, PLAY_REPEAT(2), 2); + audioQueue.playTone(BEEP_DEFAULT_FREQ+900, 80, 20, PLAY_REPEAT(2), 2); break; case AU_FRSKY_RING: - audioQueue.play(BEEP_DEFAULT_FREQ+750, 40, 20, PLAY_REPEAT(10)); - audioQueue.play(BEEP_DEFAULT_FREQ+750, 40, 80, PLAY_REPEAT(1)); - audioQueue.play(BEEP_DEFAULT_FREQ+750, 40, 20, PLAY_REPEAT(10)); + audioQueue.playTone(BEEP_DEFAULT_FREQ+750, 40, 20, PLAY_REPEAT(10)); + audioQueue.playTone(BEEP_DEFAULT_FREQ+750, 40, 80, PLAY_REPEAT(1)); + audioQueue.playTone(BEEP_DEFAULT_FREQ+750, 40, 20, PLAY_REPEAT(10)); break; case AU_FRSKY_SCIFI: - audioQueue.play(2550, 80, 20, PLAY_REPEAT(2), -1); - audioQueue.play(1950, 80, 20, PLAY_REPEAT(2), 1); - audioQueue.play(2250, 80, 20, 0); + audioQueue.playTone(2550, 80, 20, PLAY_REPEAT(2), -1); + audioQueue.playTone(1950, 80, 20, PLAY_REPEAT(2), 1); + audioQueue.playTone(2250, 80, 20, 0); break; case AU_FRSKY_ROBOT: - audioQueue.play(2250, 40, 20, PLAY_REPEAT(1)); - audioQueue.play(1650, 120, 20, PLAY_REPEAT(1)); - audioQueue.play(2550, 120, 20, PLAY_REPEAT(1)); + audioQueue.playTone(2250, 40, 20, PLAY_REPEAT(1)); + audioQueue.playTone(1650, 120, 20, PLAY_REPEAT(1)); + audioQueue.playTone(2550, 120, 20, PLAY_REPEAT(1)); break; case AU_FRSKY_CHIRP: - audioQueue.play(BEEP_DEFAULT_FREQ+1200, 40, 20, PLAY_REPEAT(2)); - audioQueue.play(BEEP_DEFAULT_FREQ+1620, 40, 20, PLAY_REPEAT(3)); + audioQueue.playTone(BEEP_DEFAULT_FREQ+1200, 40, 20, PLAY_REPEAT(2)); + audioQueue.playTone(BEEP_DEFAULT_FREQ+1620, 40, 20, PLAY_REPEAT(3)); break; case AU_FRSKY_TADA: - audioQueue.play(1650, 80, 40); - audioQueue.play(2850, 80, 40); - audioQueue.play(3450, 64, 36, PLAY_REPEAT(2)); + audioQueue.playTone(1650, 80, 40); + audioQueue.playTone(2850, 80, 40); + audioQueue.playTone(3450, 64, 36, PLAY_REPEAT(2)); break; case AU_FRSKY_CRICKET: - audioQueue.play(2550, 40, 80, PLAY_REPEAT(3)); - audioQueue.play(2550, 40, 160, PLAY_REPEAT(1)); - audioQueue.play(2550, 40, 80, PLAY_REPEAT(3)); + audioQueue.playTone(2550, 40, 80, PLAY_REPEAT(3)); + audioQueue.playTone(2550, 40, 160, PLAY_REPEAT(1)); + audioQueue.playTone(2550, 40, 80, PLAY_REPEAT(3)); break; case AU_FRSKY_SIREN: - audioQueue.play(450, 160, 40, PLAY_REPEAT(2), 2); + audioQueue.playTone(450, 160, 40, PLAY_REPEAT(2), 2); break; case AU_FRSKY_ALARMC: - audioQueue.play(1650, 32, 68, PLAY_REPEAT(2)); - audioQueue.play(2250, 64, 156, PLAY_REPEAT(1)); - audioQueue.play(1650, 64, 76, PLAY_REPEAT(2)); - audioQueue.play(2250, 32, 168, PLAY_REPEAT(1)); + audioQueue.playTone(1650, 32, 68, PLAY_REPEAT(2)); + audioQueue.playTone(2250, 64, 156, PLAY_REPEAT(1)); + audioQueue.playTone(1650, 64, 76, PLAY_REPEAT(2)); + audioQueue.playTone(2250, 32, 168, PLAY_REPEAT(1)); break; case AU_FRSKY_RATATA: - audioQueue.play(BEEP_DEFAULT_FREQ+1500, 40, 80, PLAY_REPEAT(10)); + audioQueue.playTone(BEEP_DEFAULT_FREQ+1500, 40, 80, PLAY_REPEAT(10)); break; case AU_FRSKY_TICK: - audioQueue.play(BEEP_DEFAULT_FREQ+1500, 40, 400, PLAY_REPEAT(2)); + audioQueue.playTone(BEEP_DEFAULT_FREQ+1500, 40, 400, PLAY_REPEAT(2)); break; default: break; diff --git a/radio/src/audio_arm.h b/radio/src/audio_arm.h index 2738be4c2..b6be64126 100644 --- a/radio/src/audio_arm.h +++ b/radio/src/audio_arm.h @@ -62,9 +62,11 @@ struct AudioBuffer { uint8_t state; }; -#define FRAGMENT_EMPTY 0 -#define FRAGMENT_TONE 1 -#define FRAGMENT_FILE 2 +enum FragmentTypes { + FRAGMENT_EMPTY, + FRAGMENT_TONE, + FRAGMENT_FILE, +}; struct AudioFragment { uint8_t type; @@ -107,12 +109,15 @@ class AudioContext { double step; double idx; float volume; + uint16_t freq; + uint16_t duration; + uint16_t pause; } tone; } state; inline void clear() { - fragment.clear(); + memset(this, 0, sizeof(AudioContext)); } }; @@ -128,7 +133,7 @@ class AudioQueue { void start(); - void play(uint16_t freq, uint16_t len, uint16_t pause=0, uint8_t flags=0, int8_t freqIncr=0); + void playTone(uint16_t freq, uint16_t len, uint16_t pause=0, uint8_t flags=0, int8_t freqIncr=0); void playFile(const char *filename, uint8_t flags=0, uint8_t id=0); @@ -177,7 +182,7 @@ class AudioQueue { void wakeup(); int mixAudioContext(AudioContext &context, AudioBuffer *buffer, int beepVolume, int wavVolume, unsigned int fade); - int mixBeep(AudioContext &context, AudioBuffer *buffer, int volume, unsigned int fade); + int mixTone(AudioContext &context, AudioBuffer *buffer, int volume, unsigned int fade); int mixWav(AudioContext &context, AudioBuffer *buffer, int volume, unsigned int fade); volatile bool state; @@ -252,13 +257,11 @@ void audioStart(); #define AUDIO_INACTIVITY() AUDIO_BUZZER(audioEvent(AU_INACTIVITY), beep(3)) #define AUDIO_MIX_WARNING(x) AUDIO_BUZZER(audioEvent(AU_MIX_WARNING_1+x-1), beep(1)) #define AUDIO_POT_MIDDLE(x) AUDIO_BUZZER(audioEvent(AU_STICK1_MIDDLE+x), beep(2)) -#define AUDIO_VARIO_UP() audioEvent(AU_KEYPAD_UP) -#define AUDIO_VARIO_DOWN() audioEvent(AU_KEYPAD_DOWN) #define AUDIO_TRIM_MIDDLE(f) AUDIO_BUZZER(audioEvent(AU_TRIM_MIDDLE, f), beep(2)) #define AUDIO_TRIM_END(f) AUDIO_BUZZER(audioEvent(AU_TRIM_END, f), beep(2)) #define AUDIO_TRIM(event, f) AUDIO_BUZZER(audioEvent(AU_TRIM_MOVE, f), { if (!IS_KEY_FIRST(event)) warble = true; beep(1); }) #define AUDIO_PLAY(p) audioEvent(p) -#define AUDIO_VARIO(f, t) audioQueue.play(f, t, 0, PLAY_BACKGROUND) +#define AUDIO_VARIO(f, t) audioQueue.playTone(f, t, 0, PLAY_BACKGROUND) #if defined(PCBTARANIS) #define AUDIO_A1_ORANGE() audioEvent(AU_A1_ORANGE) diff --git a/radio/src/maths.cpp b/radio/src/maths.cpp index 5874cece7..ea049823d 100644 --- a/radio/src/maths.cpp +++ b/radio/src/maths.cpp @@ -159,6 +159,7 @@ void varioWakeup() if ((int16_t)(s_varioTmr - tmr10ms) < 0) { #if defined(CPUARM) + s_varioTmr = tmr10ms; int varioBeepFreq, varioBeepTime; if (verticalSpeed > varioCenterMin) { varioBeepFreq = VARIO_FREQUENCY_ZERO + (g_eeGeneral.varioPitch*10) + (((VARIO_FREQUENCY_RANGE+(g_eeGeneral.varioRange*10)) * verticalSpeed) / varioMax); @@ -167,13 +168,11 @@ void varioWakeup() if (verticalSpeed >= varioCenterMax || varioCenterMin == varioCenterMax) varioBeepTime = period / 4; else - varioBeepTime = period * (172 - ((verticalSpeed-varioCenterMin) * 64 / (varioCenterMax-varioCenterMin))) / 256; - s_varioTmr = tmr10ms + (period/10); + varioBeepTime = period * (85 - ((verticalSpeed-varioCenterMin) * 25 / (varioCenterMax-varioCenterMin))) / 100; } else { varioBeepFreq = VARIO_FREQUENCY_ZERO + (g_eeGeneral.varioPitch*10) - (((VARIO_FREQUENCY_ZERO+(g_eeGeneral.varioPitch*10)-BEEP_MIN_FREQ) * verticalSpeed) / varioMin); varioBeepTime = 80; // TODO 20 // continuous beep: we will enter again here before the tone ends - s_varioTmr = tmr10ms + 1; } #else uint8_t varioBeepFreq, varioBeepTime; @@ -187,7 +186,6 @@ void varioWakeup() } s_varioTmr = tmr10ms + (varioBeepTime/2); #endif - AUDIO_VARIO(varioBeepFreq, varioBeepTime); } #endif From 8023606223395cd3521693a47b7f0608dce4855d Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Tue, 18 Feb 2014 16:28:25 +0100 Subject: [PATCH 10/89] A little bit expo (x^2) in repeat frequency --- radio/src/maths.cpp | 3 +-- radio/src/opentx.cpp | 2 +- radio/src/opentx.h | 2 +- 3 files changed, 3 insertions(+), 4 deletions(-) diff --git a/radio/src/maths.cpp b/radio/src/maths.cpp index ea049823d..727814ded 100644 --- a/radio/src/maths.cpp +++ b/radio/src/maths.cpp @@ -163,8 +163,7 @@ void varioWakeup() int varioBeepFreq, varioBeepTime; if (verticalSpeed > varioCenterMin) { varioBeepFreq = VARIO_FREQUENCY_ZERO + (g_eeGeneral.varioPitch*10) + (((VARIO_FREQUENCY_RANGE+(g_eeGeneral.varioRange*10)) * verticalSpeed) / varioMax); - int period = VARIO_REPEAT_ZERO + (g_eeGeneral.varioRepeat*10); - period -= ((period-VARIO_REPEAT_MAX) * verticalSpeed) / varioMax; + int period = VARIO_REPEAT_MAX + ((VARIO_REPEAT_ZERO+(g_eeGeneral.varioRepeat*10)-VARIO_REPEAT_MAX) * verticalSpeed * verticalSpeed) / (varioMax * varioMax); if (verticalSpeed >= varioCenterMax || varioCenterMin == varioCenterMax) varioBeepTime = period / 4; else diff --git a/radio/src/opentx.cpp b/radio/src/opentx.cpp index 33c2d82dd..1ddbbf449 100644 --- a/radio/src/opentx.cpp +++ b/radio/src/opentx.cpp @@ -2538,7 +2538,7 @@ uint8_t checkTrim(uint8_t event) thro = (idx==THR_STICK && g_model.thrTrim); #endif int8_t trimInc = g_model.trimInc + 1; - int8_t v = (trimInc==-1) ? min(32, abs(before)/4+1) : (1 << trimInc); + int8_t v = (trimInc==-1) ? min(32, abs(before)/4+1) : (1 << trimInc); // TODO flash saving if (trimInc < 0) if (thro) v = 4; // if throttle trim and trim trottle then step=4 int16_t after = (k&1) ? before + v : before - v; // positive = k&1 #if defined(CPUARM) diff --git a/radio/src/opentx.h b/radio/src/opentx.h index b3bd33125..3800abe29 100644 --- a/radio/src/opentx.h +++ b/radio/src/opentx.h @@ -1334,7 +1334,7 @@ enum FunctionsActive { #define VARIO_FREQUENCY_ZERO 700/*Hz*/ #define VARIO_FREQUENCY_RANGE 1000/*Hz*/ #define VARIO_REPEAT_ZERO 500/*ms*/ -#define VARIO_REPEAT_MAX 50/*ms*/ +#define VARIO_REPEAT_MAX 80/*ms*/ extern MASK_FUNC_TYPE activeFunctions; extern MASK_CFN_TYPE activeFnSwitches; From f9590d4141ed295055d87720052e3d8dbc11431b Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Tue, 18 Feb 2014 20:44:10 +0100 Subject: [PATCH 11/89] Vario bugfixes --- radio/src/audio_arm.cpp | 87 ++++++++++++++++++++------------------ radio/src/audio_arm.h | 49 +++++++++++++--------- radio/src/maths.cpp | 93 ++++++++++++++++++++++++++--------------- 3 files changed, 135 insertions(+), 94 deletions(-) diff --git a/radio/src/audio_arm.cpp b/radio/src/audio_arm.cpp index f9a9bc38d..4c374dc73 100644 --- a/radio/src/audio_arm.cpp +++ b/radio/src/audio_arm.cpp @@ -452,35 +452,35 @@ int AudioQueue::mixWav(AudioContext &context, AudioBuffer *buffer, int volume, u AudioFragment & fragment = context.fragment; if (fragment.file[1]) { - result = f_open(&context.state.wav.file, fragment.file, FA_OPEN_EXISTING | FA_READ); + result = f_open(&context.wav.file, fragment.file, FA_OPEN_EXISTING | FA_READ); fragment.file[1] = 0; if (result == FR_OK) { - result = f_read(&context.state.wav.file, wavBuffer, RIFF_CHUNK_SIZE+8, &read); + result = f_read(&context.wav.file, wavBuffer, RIFF_CHUNK_SIZE+8, &read); if (result == FR_OK && read == RIFF_CHUNK_SIZE+8 && !memcmp(wavBuffer, "RIFF", 4) && !memcmp(wavBuffer+8, "WAVEfmt ", 8)) { uint32_t size = *((uint32_t *)(wavBuffer+16)); - result = (size < 256 ? f_read(&context.state.wav.file, wavBuffer, size+8, &read) : FR_DENIED); + result = (size < 256 ? f_read(&context.wav.file, wavBuffer, size+8, &read) : FR_DENIED); if (result == FR_OK && read == size+8) { - context.state.wav.codec = ((uint16_t *)wavBuffer)[0]; - context.state.wav.freq = ((uint16_t *)wavBuffer)[2]; + context.wav.codec = ((uint16_t *)wavBuffer)[0]; + context.wav.freq = ((uint16_t *)wavBuffer)[2]; uint32_t *wavSamplesPtr = (uint32_t *)(wavBuffer + size); uint32_t size = wavSamplesPtr[1]; - if (context.state.wav.freq != 0 && context.state.wav.freq * (AUDIO_SAMPLE_RATE / context.state.wav.freq) == AUDIO_SAMPLE_RATE) { - context.state.wav.resampleRatio = (AUDIO_SAMPLE_RATE / context.state.wav.freq); - context.state.wav.readSize = (context.state.wav.codec == CODEC_ID_PCM_S16LE ? 2*AUDIO_BUFFER_SIZE : AUDIO_BUFFER_SIZE) / context.state.wav.resampleRatio; + if (context.wav.freq != 0 && context.wav.freq * (AUDIO_SAMPLE_RATE / context.wav.freq) == AUDIO_SAMPLE_RATE) { + context.wav.resampleRatio = (AUDIO_SAMPLE_RATE / context.wav.freq); + context.wav.readSize = (context.wav.codec == CODEC_ID_PCM_S16LE ? 2*AUDIO_BUFFER_SIZE : AUDIO_BUFFER_SIZE) / context.wav.resampleRatio; } else { result = FR_DENIED; } while (result == FR_OK && memcmp(wavSamplesPtr, "data", 4) != 0) { - result = f_lseek(&context.state.wav.file, f_tell(&context.state.wav.file)+size); + result = f_lseek(&context.wav.file, f_tell(&context.wav.file)+size); if (result == FR_OK) { - result = f_read(&context.state.wav.file, wavBuffer, 8, &read); + result = f_read(&context.wav.file, wavBuffer, 8, &read); if (read != 8) result = FR_DENIED; wavSamplesPtr = (uint32_t *)wavBuffer; size = wavSamplesPtr[1]; } } - context.state.wav.size = size; + context.wav.size = size; } else { result = FR_DENIED; @@ -494,34 +494,34 @@ int AudioQueue::mixWav(AudioContext &context, AudioBuffer *buffer, int volume, u read = 0; if (result == FR_OK) { - result = f_read(&context.state.wav.file, wavBuffer, context.state.wav.readSize, &read); + result = f_read(&context.wav.file, wavBuffer, context.wav.readSize, &read); if (result == FR_OK) { - if (read > context.state.wav.size) { - read = context.state.wav.size; + if (read > context.wav.size) { + read = context.wav.size; } - context.state.wav.size -= read; + context.wav.size -= read; - if (read != context.state.wav.readSize) { - f_close(&context.state.wav.file); + if (read != context.wav.readSize) { + f_close(&context.wav.file); fragment.clear(); } uint16_t * samples = buffer->data; - if (context.state.wav.codec == CODEC_ID_PCM_S16LE) { + if (context.wav.codec == CODEC_ID_PCM_S16LE) { read /= 2; for (uint32_t i=0; i 0) { int points; - double toneIdx = context.state.tone.idx; + double toneIdx = context.tone.idx; - if (fragment.tone.freq != context.state.tone.freq) { - context.state.tone.freq = fragment.tone.freq; - context.state.tone.step = double(DIM(sineValues)*fragment.tone.freq) / AUDIO_SAMPLE_RATE; - context.state.tone.volume = evalVolumeRatio(fragment.tone.freq, volume); + if (fragment.tone.reset) { + context.tone.duration = 0; + context.tone.pause = 0; + } + + if (fragment.tone.freq != context.tone.freq) { + context.tone.freq = fragment.tone.freq; + context.tone.step = double(DIM(sineValues)*fragment.tone.freq) / AUDIO_SAMPLE_RATE; + context.tone.volume = evalVolumeRatio(fragment.tone.freq, volume); } if (fragment.tone.freqIncr) { @@ -577,38 +582,37 @@ int AudioQueue::mixTone(AudioContext &context, AudioBuffer *buffer, int volume, else { duration = remainingDuration; points = (duration * AUDIO_BUFFER_SIZE) / AUDIO_BUFFER_DURATION; - unsigned int end = toneIdx + (context.state.tone.step * points); + unsigned int end = toneIdx + (context.tone.step * points); if (end > DIM(sineValues)) end -= (end % DIM(sineValues)); else end = DIM(sineValues); - points = (double(end) - toneIdx) / context.state.tone.step; + points = (double(end) - toneIdx) / context.tone.step; } for (int i=0; idata[i], sample, fade); - toneIdx += context.state.tone.step; + toneIdx += context.tone.step; if ((unsigned int)toneIdx >= DIM(sineValues)) toneIdx -= DIM(sineValues); } if (remainingDuration > AUDIO_BUFFER_DURATION) { - context.state.tone.duration += AUDIO_BUFFER_DURATION; - context.state.tone.idx = toneIdx; + context.tone.duration += AUDIO_BUFFER_DURATION; + context.tone.idx = toneIdx; return AUDIO_BUFFER_SIZE; } else { - context.state.tone.duration = 32000; // once the tone is finished, it's not possible to update its frequency and duration - context.state.tone.idx = 0; + context.tone.duration = 32000; // once the tone is finished, it's not possible to update its frequency and duration } } - remainingDuration = fragment.tone.pause - context.state.tone.pause; + remainingDuration = fragment.tone.pause - context.tone.pause; if (remainingDuration > 0) { result = AUDIO_BUFFER_SIZE; - context.state.tone.pause += min(AUDIO_BUFFER_DURATION-duration, fragment.tone.pause); - if (fragment.tone.pause > context.state.tone.pause) + context.tone.pause += min(AUDIO_BUFFER_DURATION-duration, fragment.tone.pause); + if (fragment.tone.pause > context.tone.pause) return result; } @@ -729,10 +733,13 @@ void AudioQueue::playTone(uint16_t freq, uint16_t len, uint16_t pause, uint8_t f if (flags & PLAY_BACKGROUND) { AudioFragment & fragment = backgroundContext.fragment; + if (fragment.type != FRAGMENT_TONE) + backgroundContext.clear(); fragment.type = FRAGMENT_TONE; fragment.tone.freq = freq; fragment.tone.duration = len; fragment.tone.pause = pause; + fragment.tone.reset = (flags & PLAY_NOW); } else { freq += g_eeGeneral.speakerPitch * 15; diff --git a/radio/src/audio_arm.h b/radio/src/audio_arm.h index b6be64126..40be7179a 100644 --- a/radio/src/audio_arm.h +++ b/radio/src/audio_arm.h @@ -78,6 +78,7 @@ struct AudioFragment { uint16_t duration; uint16_t pause; int8_t freqIncr; + uint8_t reset; } tone; char file[AUDIO_FILENAME_MAXLEN+1]; @@ -93,31 +94,39 @@ class AudioContext { public: AudioFragment fragment; - union { #if defined(SDCARD) - struct { - FIL file; - uint8_t codec; - uint32_t freq; - uint32_t size; - uint8_t resampleRatio; - uint16_t readSize; - } wav; + struct { + FIL file; + uint8_t codec; + uint32_t freq; + uint32_t size; + uint8_t resampleRatio; + uint16_t readSize; + } wav; #endif - struct { - double step; - double idx; - float volume; - uint16_t freq; - uint16_t duration; - uint16_t pause; - } tone; - } state; + struct { + double step; + double idx; + float volume; + uint16_t freq; + uint16_t duration; + uint16_t pause; + inline void clear() + { + step = 0; + idx = 0; + volume = 0; + freq = 0; + duration = 0; + pause = 0; + } + } tone; inline void clear() { - memset(this, 0, sizeof(AudioContext)); + fragment.clear(); + tone.clear(); } }; @@ -261,7 +270,7 @@ void audioStart(); #define AUDIO_TRIM_END(f) AUDIO_BUZZER(audioEvent(AU_TRIM_END, f), beep(2)) #define AUDIO_TRIM(event, f) AUDIO_BUZZER(audioEvent(AU_TRIM_MOVE, f), { if (!IS_KEY_FIRST(event)) warble = true; beep(1); }) #define AUDIO_PLAY(p) audioEvent(p) -#define AUDIO_VARIO(f, t) audioQueue.playTone(f, t, 0, PLAY_BACKGROUND) +#define AUDIO_VARIO(fq, t, p, f) audioQueue.playTone(fq, t, p, f) #if defined(PCBTARANIS) #define AUDIO_A1_ORANGE() audioEvent(AU_A1_ORANGE) diff --git a/radio/src/maths.cpp b/radio/src/maths.cpp index 727814ded..67456c95d 100644 --- a/radio/src/maths.cpp +++ b/radio/src/maths.cpp @@ -114,7 +114,53 @@ void getGpsDistance() } #endif -#if defined(FRSKY) && defined(VARIO) +#if defined(CPUARM) + +void varioWakeup() +{ + if (isFunctionActive(FUNCTION_VARIO)) { + int varioFreq, varioDuration, varioPause=0; + uint8_t varioFlags; + +#if 1 + #warning "Ele stick for vario tests" + int verticalSpeed = getValue(MIXSRC_Ele); +#else + int verticalSpeed = frskyData.hub.varioSpeed; +#endif + + int varioCenterMin = (int)g_model.frsky.varioCenterMin * 10 - 50; + int varioCenterMax = (int)g_model.frsky.varioCenterMax * 10 + 50; + int varioMax = (10+(int)g_model.frsky.varioMax) * 100; + int varioMin = (-10+(int)g_model.frsky.varioMin) * 100; + + if (verticalSpeed > varioMax) + verticalSpeed = varioMax; + else if (verticalSpeed < varioMin) + verticalSpeed = varioMin; + + if (verticalSpeed > varioCenterMin) { + varioFreq = VARIO_FREQUENCY_ZERO + (g_eeGeneral.varioPitch*10) + (((VARIO_FREQUENCY_RANGE+(g_eeGeneral.varioRange*10)) * verticalSpeed) / varioMax); + int varioPeriod = VARIO_REPEAT_MAX + ((VARIO_REPEAT_ZERO+(g_eeGeneral.varioRepeat*10)-VARIO_REPEAT_MAX) * (varioMax-verticalSpeed) * (varioMax-verticalSpeed)) / (varioMax * varioMax); + if (verticalSpeed >= varioCenterMax || varioCenterMin == varioCenterMax) + varioDuration = varioPeriod / 4; + else + varioDuration = varioPeriod * (85 - (((verticalSpeed-varioCenterMin) * 25) / (varioCenterMax-varioCenterMin))) / 100; + varioPause = varioPeriod - varioDuration; + varioFlags = PLAY_BACKGROUND; + } + else { + varioFreq = VARIO_FREQUENCY_ZERO + (g_eeGeneral.varioPitch*10) - (((VARIO_FREQUENCY_ZERO+(g_eeGeneral.varioPitch*10)-BEEP_MIN_FREQ) * verticalSpeed) / varioMin); + varioDuration = 80; // TODO 20 // continuous beep: we will enter again here before the tone ends + varioFlags = PLAY_BACKGROUND|PLAY_NOW; + } + + AUDIO_VARIO(varioFreq, varioDuration, varioPause, varioFlags); + } +} + +#elif defined(FRSKY) && defined(VARIO) + void varioWakeup() { static tmr10ms_t s_varioTmr; @@ -123,12 +169,7 @@ void varioWakeup() if (isFunctionActive(FUNCTION_VARIO)) { #if defined(AUDIO) cli(); -#if 1 - #warning "Ele stick for vario tests" - int verticalSpeed = getValue(MIXSRC_Ele); -#else int verticalSpeed = frskyData.hub.varioSpeed; -#endif sei(); #if defined(PCBSTD) @@ -140,10 +181,10 @@ void varioWakeup() verticalSpeed = (verticalSpeed * 10) / ((varioMax-varioCenterMax) / 100); if ((int16_t)(s_varioTmr-tmr10ms) < 0) { - uint8_t varioBeepFreq = (verticalSpeed * 10 + 16000) >> 8; - uint8_t varioBeepTime = (1600 - verticalSpeed) / 100; - s_varioTmr = tmr10ms + (varioBeepTime*2); - AUDIO_VARIO(varioBeepFreq, varioBeepTime); + uint8_t varioFreq = (verticalSpeed * 10 + 16000) >> 8; + uint8_t varioDuration = (1600 - verticalSpeed) / 100; + s_varioTmr = tmr10ms + (varioDuration*2); + AUDIO_VARIO(varioFreq, varioDuration); } } #else @@ -158,34 +199,17 @@ void varioWakeup() verticalSpeed = varioMin; if ((int16_t)(s_varioTmr - tmr10ms) < 0) { -#if defined(CPUARM) - s_varioTmr = tmr10ms; - int varioBeepFreq, varioBeepTime; - if (verticalSpeed > varioCenterMin) { - varioBeepFreq = VARIO_FREQUENCY_ZERO + (g_eeGeneral.varioPitch*10) + (((VARIO_FREQUENCY_RANGE+(g_eeGeneral.varioRange*10)) * verticalSpeed) / varioMax); - int period = VARIO_REPEAT_MAX + ((VARIO_REPEAT_ZERO+(g_eeGeneral.varioRepeat*10)-VARIO_REPEAT_MAX) * verticalSpeed * verticalSpeed) / (varioMax * varioMax); - if (verticalSpeed >= varioCenterMax || varioCenterMin == varioCenterMax) - varioBeepTime = period / 4; - else - varioBeepTime = period * (85 - ((verticalSpeed-varioCenterMin) * 25 / (varioCenterMax-varioCenterMin))) / 100; - } - else { - varioBeepFreq = VARIO_FREQUENCY_ZERO + (g_eeGeneral.varioPitch*10) - (((VARIO_FREQUENCY_ZERO+(g_eeGeneral.varioPitch*10)-BEEP_MIN_FREQ) * verticalSpeed) / varioMin); - varioBeepTime = 80; // TODO 20 // continuous beep: we will enter again here before the tone ends - } -#else - uint8_t varioBeepFreq, varioBeepTime; + uint8_t varioFreq, varioDuration; if (verticalSpeed > 0) { - varioBeepFreq = (verticalSpeed * 4 + 8000) >> 7; - varioBeepTime = (8000 - verticalSpeed * 5) / 100; + varioFreq = (verticalSpeed * 4 + 8000) >> 7; + varioDuration = (8000 - verticalSpeed * 5) / 100; } else { - varioBeepFreq = (verticalSpeed * 3 + 8000) >> 7; - varioBeepTime = 20; + varioFreq = (verticalSpeed * 3 + 8000) >> 7; + varioDuration = 20; } - s_varioTmr = tmr10ms + (varioBeepTime/2); -#endif - AUDIO_VARIO(varioBeepFreq, varioBeepTime); + s_varioTmr = tmr10ms + (varioDuration/2); + AUDIO_VARIO(varioFreq, varioDuration); } #endif @@ -217,4 +241,5 @@ void varioWakeup() s_varioTmr = tmr10ms; } } + #endif From fbd07444314d7bf23dcfdcf711cd52bb046f102e Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Tue, 18 Feb 2014 22:43:17 +0100 Subject: [PATCH 12/89] Issue #713 - 64 custom functions instead of 32. 8chars only filenames in PlayTrack function --- companion/src/eeprominterface.h | 2 +- companion/src/firmwares/opentx/opentxeeprom.cpp | 6 ++++-- companion/src/firmwares/opentx/opentxinterface.cpp | 4 ++-- radio/src/eeprom_conversions.cpp | 6 +++--- radio/src/myeeprom.h | 6 +++--- 5 files changed, 13 insertions(+), 11 deletions(-) diff --git a/companion/src/eeprominterface.h b/companion/src/eeprominterface.h index 60f99b41a..14dc0d7ac 100644 --- a/companion/src/eeprominterface.h +++ b/companion/src/eeprominterface.h @@ -74,7 +74,7 @@ const uint8_t modn12x3[4][4]= { #define C9X_MAX_ENCODERS 2 #define C9X_NUM_CHNOUT 32 // number of real output channels #define C9X_NUM_CSW 32 // number of custom switches -#define C9X_MAX_CUSTOM_FUNCTIONS 32 // number of functions assigned to switches +#define C9X_MAX_CUSTOM_FUNCTIONS 64 // number of functions assigned to switches #define C9X_NUM_MODULES 2 #define STK_RUD 1 diff --git a/companion/src/firmwares/opentx/opentxeeprom.cpp b/companion/src/firmwares/opentx/opentxeeprom.cpp index 92b5c4b3e..c078e6009 100644 --- a/companion/src/firmwares/opentx/opentxeeprom.cpp +++ b/companion/src/firmwares/opentx/opentxeeprom.cpp @@ -20,7 +20,7 @@ #define MAX_CHANNELS(board, version) (IS_ARM(board) ? 32 : 16) #define MAX_EXPOS(board, version) (IS_ARM(board) ? ((IS_TARANIS(board) && version >= 216) ? 64 : 32) : (IS_DBLRAM(board, version) ? 16 : 14)) #define MAX_CUSTOM_SWITCHES(board, version) (IS_ARM(board) ? 32 : (IS_DBLEEPROM(board, version) ? 15 : 12)) -#define MAX_CUSTOM_FUNCTIONS(board, version) (IS_ARM(board) ? 32 : (IS_DBLEEPROM(board, version) ? 24 : 16)) +#define MAX_CUSTOM_FUNCTIONS(board, version) (IS_ARM(board) ? (version >= 216 ? 64 : 32) : (IS_DBLEEPROM(board, version) ? 24 : 16)) #define MAX_CURVES(board, version) (IS_ARM(board) ? ((IS_TARANIS(board) && version >= 216) ? 32 : 16) : O9X_MAX_CURVES) #define MAX_GVARS(board, version) ((IS_ARM(board) && version >= 216) ? 9 : 5) @@ -1424,7 +1424,9 @@ class ArmCustomFunctionField: public TransformedField { internalField.Append(new SwitchField<8>(fn.swtch, board, version)); internalField.Append(new ConversionField< UnsignedField<8> >((unsigned int &)fn.func, &functionsConversionTable, "Function", ::QObject::tr("OpenTX on this board doesn't accept this function"))); - if (IS_TARANIS(board)) + if (IS_TARANIS(board) && version >= 216) + internalField.Append(new CharField<8>(_param, false)); + else if (IS_TARANIS(board)) internalField.Append(new CharField<10>(_param, false)); else internalField.Append(new CharField<6>(_param, false)); diff --git a/companion/src/firmwares/opentx/opentxinterface.cpp b/companion/src/firmwares/opentx/opentxinterface.cpp index 16dbfeca9..d61ef76f6 100644 --- a/companion/src/firmwares/opentx/opentxinterface.cpp +++ b/companion/src/firmwares/opentx/opentxinterface.cpp @@ -521,7 +521,7 @@ int Open9xInterface::getCapability(const Capability capability) return (IS_TARANIS(board) ? 22 : 9); case CustomFunctions: if (IS_ARM(board)) - return 32; + return 64; else if (board==BOARD_GRUVIN9X||board==BOARD_M128) return 24; else @@ -554,7 +554,7 @@ int Open9xInterface::getCapability(const Capability capability) case VoicesAsNumbers: return (IS_ARM(board) ? 0 : 1); case VoicesMaxLength: - return (IS_ARM(board) ? (IS_TARANIS(board) ? 10 : 6) : 0); + return (IS_ARM(board) ? (IS_TARANIS(board) ? 8 : 6) : 0); case MultiLangVoice: return (IS_ARM(board) ? 1 : 0); case SoundPitch: diff --git a/radio/src/eeprom_conversions.cpp b/radio/src/eeprom_conversions.cpp index 8a0e6bac9..6e1a5924b 100644 --- a/radio/src/eeprom_conversions.cpp +++ b/radio/src/eeprom_conversions.cpp @@ -144,7 +144,7 @@ PACK(typedef struct { int8_t swtch; uint8_t func; PACK(union { - char name[LEN_CFN_NAME]; + char name[10]; struct { int16_t val; int16_t ext1; @@ -193,7 +193,7 @@ PACK(typedef struct { int8_t points[NUM_POINTS]; LogicalSwitchData_v215 customSw[NUM_CSW]; - CustomFnData_v215 funcSw[NUM_CFN]; + CustomFnData_v215 funcSw[32]; SwashRingData swashR; PhaseData_v215 phaseData[MAX_PHASES]; @@ -575,7 +575,7 @@ void ConvertModel_215_to_216(ModelData &model) } if (fn.func == FUNC_PLAY_TRACK || fn.func == FUNC_BACKGND_MUSIC) { - memcpy(fn.play.name, oldModel.funcSw[i].param.name, LEN_CFN_NAME); + memcpy(fn.play.name, oldModel.funcSw[i].param.name, 8); } else { fn.all.val = oldModel.funcSw[i].param.composite.val; diff --git a/radio/src/myeeprom.h b/radio/src/myeeprom.h index fed0158f4..0f2e0076b 100644 --- a/radio/src/myeeprom.h +++ b/radio/src/myeeprom.h @@ -74,7 +74,7 @@ #define MAX_MIXERS 64 #define MAX_EXPOS 64 #define NUM_CSW 32 // number of custom switches - #define NUM_CFN 32 // number of functions assigned to switches + #define NUM_CFN 64 // number of functions assigned to switches #define MAX_SCRIPTS 3 #define MAX_INPUTS 32 #elif defined(CPUARM) @@ -84,7 +84,7 @@ #define MAX_MIXERS 64 #define MAX_EXPOS 32 #define NUM_CSW 32 // number of custom switches - #define NUM_CFN 32 // number of functions assigned to switches + #define NUM_CFN 64 // number of functions assigned to switches #elif defined(CPUM2560) || defined(CPUM2561) #define MAX_MODELS 30 #define NUM_CHNOUT 16 // number of real output channels CH1-CH16 @@ -806,7 +806,7 @@ enum AdjustGvarFunctionParam { #if defined(CPUARM) #if defined(PCBTARANIS) - #define LEN_CFN_NAME 10 + #define LEN_CFN_NAME 8 #else #define LEN_CFN_NAME 6 #endif From e38a4d320f4e7e2378563ebafaa9cac0e8336a76 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Wed, 19 Feb 2014 10:41:03 +0100 Subject: [PATCH 13/89] Issue #713 - Automatic Switch Audio Files (part 1) --- radio/src/audio_arm.cpp | 219 +++++++++++++++++---------- radio/src/audio_arm.h | 32 ++-- radio/src/eeprom_raw.cpp | 2 +- radio/src/eeprom_rlc.cpp | 2 +- radio/src/opentx.h | 3 +- radio/src/simpgmspace.cpp | 7 +- radio/src/targets/sky9x/diskio.cpp | 4 +- radio/src/targets/taranis/diskio.cpp | 2 +- 8 files changed, 166 insertions(+), 105 deletions(-) diff --git a/radio/src/audio_arm.cpp b/radio/src/audio_arm.cpp index 5d2fb1be9..ea4af817c 100644 --- a/radio/src/audio_arm.cpp +++ b/radio/src/audio_arm.cpp @@ -117,132 +117,190 @@ const char * audioFilenames[] = { }; uint64_t sdAvailableSystemAudioFiles = 0; -uint8_t sdAvailablePhaseAudioFiles[MAX_PHASES] = { 0 }; -uint8_t sdAvailableMixerAudioFiles[MAX_MIXERS] = { 0 }; +uint32_t sdAvailablePhaseAudioFiles = 0; +uint32_t sdAvailableSwitchAudioFiles = 0; +uint64_t sdAvailableLogicalSwitchAudioFiles = 0; -void refreshSystemAudioFiles() +#define MASK_SYSTEM_AUDIO_FILE(index) ((uint64_t)1 << index) +#define MASK_PHASE_AUDIO_FILE(index, event) ((uint32_t)1 << (2*index+event)) +#define MASK_SWITCH_AUDIO_FILE(index) ((uint32_t)1 << index) +#define MASK_LOGICAL_SWITCH_AUDIO_FILE(index, event) ((uint64_t)1 << (2*index+event)) + +bool isFileAvailable(const char * filename) { FILINFO info; -#if _USE_LFN TCHAR lfn[_MAX_LFN + 1]; info.lfname = lfn; info.lfsize = sizeof(lfn); -#endif + return f_stat(filename, &info) == FR_OK; +} - char filename[32] = SYSTEM_SOUNDS_PATH "/"; +void getSystemAudioFile(char * filename, int index) +{ + strcpy(filename, SYSTEM_SOUNDS_PATH "/"); strncpy(filename+SOUNDS_PATH_LNG_OFS, currentLanguagePack->id, 2); + strcpy(filename+sizeof(SYSTEM_SOUNDS_PATH), audioFilenames[index]); + strcat(filename+sizeof(SYSTEM_SOUNDS_PATH), SOUNDS_EXT); +} + +void referenceSystemAudioFiles() +{ + char filename[AUDIO_FILENAME_MAXLEN+1]; + uint64_t availableAudioFiles = 0; assert(sizeof(audioFilenames)==AU_FRSKY_FIRST*sizeof(char *)); assert(sizeof(sdAvailableSystemAudioFiles)*8 >= AU_FRSKY_FIRST); - uint64_t availableAudioFiles = 0; - - for (uint32_t i=0; iid, 2); - - if (sdMounted()) { - char *buf = strcat_modelname(&filename[sizeof(SOUNDS_PATH)], g_eeGeneral.currModel); - *buf++ = '/'; + char *str = strcat_modelname(filename+sizeof(SOUNDS_PATH), g_eeGeneral.currModel); + *str++ = '/'; + char * tmp = strcat_phasename(str, index); + strcpy(tmp, suffixes[event]); + strcat(tmp, SOUNDS_EXT); +} - for (uint32_t i=0; iid, 2); + char *str = strcat_modelname(filename+sizeof(SOUNDS_PATH), g_eeGeneral.currModel); + *str++ = '/'; + int len = STR_VSWITCHES[0]; + strncpy(str, &STR_VSWITCHES[1+len*index], len); + str += len-1; + if (*str == '\300') { + strcpy(str, "-up"); + str += 3; + } + else if (*str == '-') { + strcpy(str, "-mid"); + str += 4; + } + else if (*str == '\301') { + strcpy(str, "-down"); + str += 5; + } + else { + str += 1; + } + strcat(str, SOUNDS_EXT); +} + +void getLogicalSwitchAudioFile(char * filename, int index, unsigned int event) +{ + strcpy(filename, SOUNDS_PATH "/"); + strncpy(filename+SOUNDS_PATH_LNG_OFS, currentLanguagePack->id, 2); + char *str = strcat_modelname(filename+sizeof(SOUNDS_PATH), g_eeGeneral.currModel); + *str++ = '/'; + int len = STR_VSWITCHES[0]; + strncpy(str, &STR_VSWITCHES[1+len*(index+SWSRC_FIRST_CSW-1)], len); + str += len; + strcpy(str, suffixes[event]); + strcat(str, SOUNDS_EXT); +} + +void referenceModelAudioFiles() +{ + char filename[AUDIO_FILENAME_MAXLEN+1]; + + { + // Phases Audio Files -[on|off].wav + uint32_t mask = 0; + for (int i=0; i-[up|mid|down].wav + uint32_t mask = 0; + for (int i=0; i-[on|off].wav + uint64_t mask = 0; + for (int i=0; i> 24); uint8_t index = (i >> 16) & 0xFF; uint8_t event = i & 0xFF; #if 0 - printf("isAudioFileAvailable(%08x)\n", i); fflush(stdout); + printf("isAudioFileReferenced(%08x)\n", i); fflush(stdout); #endif if (category == SYSTEM_AUDIO_CATEGORY) { - if (sdAvailableSystemAudioFiles & ((uint64_t)1 << event)) { - strcpy(filename, SYSTEM_SOUNDS_PATH "/"); - strncpy(filename+SOUNDS_PATH_LNG_OFS, currentLanguagePack->id, 2); - strcpy(filename+sizeof(SYSTEM_SOUNDS_PATH), audioFilenames[i]); - strcat(filename+sizeof(SYSTEM_SOUNDS_PATH), SOUNDS_EXT); + if (sdAvailableSystemAudioFiles & MASK_SYSTEM_AUDIO_FILE(index)) { + getSystemAudioFile(filename, index); return true; } } else if (category == PHASE_AUDIO_CATEGORY) { - if (sdAvailablePhaseAudioFiles[index] & ((uint32_t)1 << event)) { - strcpy(filename, SOUNDS_PATH "/"); - strncpy(filename+SOUNDS_PATH_LNG_OFS, currentLanguagePack->id, 2); - char *str = strcat_modelname(filename+sizeof(SOUNDS_PATH), g_eeGeneral.currModel); - *str++ = '/'; - char * tmp = strcat_phasename(str, index); - if (tmp != str) { - strcpy(tmp, suffixes[event]); - strcat(tmp, SOUNDS_EXT); - return true; - } + if (sdAvailablePhaseAudioFiles & MASK_PHASE_AUDIO_FILE(index, event)) { + getPhaseAudioFile(filename, index, event); + return true; } } - else if (category == MIXER_AUDIO_CATEGORY) { - if (sdAvailableMixerAudioFiles[index] & ((uint32_t)1 << event)) { - strcpy(filename, SOUNDS_PATH "/"); - strncpy(filename+SOUNDS_PATH_LNG_OFS, currentLanguagePack->id, 2); - char *str = strcat_modelname(filename+sizeof(SOUNDS_PATH), g_eeGeneral.currModel); - *str++ = '/'; - char * tmp = strcat_mixername(str, index); - if (tmp != str) { - strcpy(tmp, suffixes[event]); - strcat(tmp, SOUNDS_EXT); - return true; - } + else if (category == SWITCH_AUDIO_CATEGORY) { + if (sdAvailableSwitchAudioFiles & MASK_SWITCH_AUDIO_FILE(index)) { + getSwitchAudioFile(filename, index); + return true; + } + } + else if (category == LOGICAL_SWITCH_AUDIO_CATEGORY) { + if (sdAvailableLogicalSwitchAudioFiles & MASK_LOGICAL_SWITCH_AUDIO_FILE(index, event)) { + getLogicalSwitchAudioFile(filename, index, event); + return true; } } return false; } #else -#define isAudioFileAvailable(i, f) false +#define isAudioFileReferenced(i, f) false #endif +// TODO should be generated and in flash rather than in ram int16_t alawTable[256]; int16_t ulawTable[256]; @@ -757,10 +815,6 @@ void AudioQueue::reset() void audioEvent(uint8_t e, uint16_t f) { -#if defined(SDCARD) - char filename[AUDIO_FILENAME_MAXLEN+1]; -#endif - #if defined(HAPTIC) haptic.event(e); //do this before audio to help sync timings #endif @@ -773,7 +827,8 @@ void audioEvent(uint8_t e, uint16_t f) if (g_eeGeneral.beepMode>0 || (g_eeGeneral.beepMode==0 && e>=AU_TRIM_MOVE) || (g_eeGeneral.beepMode>=-1 && e<=AU_ERROR)) { #if defined(SDCARD) - if (e < AU_FRSKY_FIRST && isAudioFileAvailable(e, filename)) { + char filename[AUDIO_FILENAME_MAXLEN+1]; + if (e < AU_FRSKY_FIRST && isAudioFileReferenced(e, filename)) { audioQueue.playFile(filename); } else diff --git a/radio/src/audio_arm.h b/radio/src/audio_arm.h index 9b45187b0..b96808426 100644 --- a/radio/src/audio_arm.h +++ b/radio/src/audio_arm.h @@ -277,16 +277,21 @@ void audioStart(); #define AUDIO_HEARTBEAT() -#define SYSTEM_AUDIO_CATEGORY 0 -#define MODEL_AUDIO_CATEGORY 1 -#define PHASE_AUDIO_CATEGORY 2 -#define MIXER_AUDIO_CATEGORY 3 +enum AutomaticPromptsCategories { + SYSTEM_AUDIO_CATEGORY, + MODEL_AUDIO_CATEGORY, + PHASE_AUDIO_CATEGORY, + SWITCH_AUDIO_CATEGORY, + LOGICAL_SWITCH_AUDIO_CATEGORY, +}; -#define AUDIO_EVENT_OFF 0 -#define AUDIO_EVENT_ON 1 -#define AUDIO_EVENT_BG 2 +enum AutomaticPromptsEvents { + AUDIO_EVENT_OFF, + AUDIO_EVENT_ON, + AUDIO_EVENT_MID, +}; -extern void pushPrompt(uint16_t prompt, uint8_t id=0); +void pushPrompt(uint16_t prompt, uint8_t id=0); #define I18N_PLAY_FUNCTION(lng, x, ...) void lng ## _ ## x(__VA_ARGS__, uint8_t id) #define PLAY_FUNCTION(x, ...) void x(__VA_ARGS__, uint8_t id) @@ -300,15 +305,16 @@ extern void pushPrompt(uint16_t prompt, uint8_t id=0); #define AUDIO_RESET() audioQueue.reset() #if defined(SDCARD) - #define PLAY_PHASE_OFF(phase) do { char filename[AUDIO_FILENAME_MAXLEN+1]; if (isAudioFileAvailable((PHASE_AUDIO_CATEGORY << 24) + (phase << 16) + AUDIO_EVENT_OFF, filename)) audioQueue.playFile(filename); } while (0) - #define PLAY_PHASE_ON(phase) do { char filename[AUDIO_FILENAME_MAXLEN+1]; if (isAudioFileAvailable((PHASE_AUDIO_CATEGORY << 24) + (phase << 16) + AUDIO_EVENT_ON, filename)) audioQueue.playFile(filename); } while (0) + #define PLAY_PHASE_OFF(phase) do { char filename[AUDIO_FILENAME_MAXLEN+1]; if (isAudioFileReferenced((PHASE_AUDIO_CATEGORY << 24) + (phase << 16) + AUDIO_EVENT_OFF, filename)) audioQueue.playFile(filename); } while (0) + #define PLAY_PHASE_ON(phase) do { char filename[AUDIO_FILENAME_MAXLEN+1]; if (isAudioFileReferenced((PHASE_AUDIO_CATEGORY << 24) + (phase << 16) + AUDIO_EVENT_ON, filename)) audioQueue.playFile(filename); } while (0) #else #define PLAY_PHASE_OFF(phase) #define PLAY_PHASE_ON(phase) #endif -extern void refreshSystemAudioFiles(); -extern void refreshModelAudioFiles(); -extern bool isAudioFileAvailable(uint32_t i, char * filename); +void referenceSystemAudioFiles(); +void referenceModelAudioFiles(); + +bool isAudioFileReferenced(uint32_t i, char * filename/*at least AUDIO_FILENAME_MAXLEN+1 long*/); #endif diff --git a/radio/src/eeprom_raw.cpp b/radio/src/eeprom_raw.cpp index 718fe3558..5050f7cbb 100644 --- a/radio/src/eeprom_raw.cpp +++ b/radio/src/eeprom_raw.cpp @@ -404,7 +404,7 @@ void eeLoadModel(uint8_t id) #endif #if defined(CPUARM) && defined(SDCARD) - refreshModelAudioFiles(); + referenceModelAudioFiles(); #endif LOAD_MODEL_BITMAP(); diff --git a/radio/src/eeprom_rlc.cpp b/radio/src/eeprom_rlc.cpp index f6f62502e..190dcdbe8 100644 --- a/radio/src/eeprom_rlc.cpp +++ b/radio/src/eeprom_rlc.cpp @@ -978,7 +978,7 @@ void eeLoadModel(uint8_t id) #endif #if defined(CPUARM) && defined(SDCARD) - refreshModelAudioFiles(); + referenceModelAudioFiles(); #endif LOAD_MODEL_BITMAP(); diff --git a/radio/src/opentx.h b/radio/src/opentx.h index dcfed29a4..b6a555b11 100644 --- a/radio/src/opentx.h +++ b/radio/src/opentx.h @@ -1616,8 +1616,7 @@ uint8_t zlen(const char *str, uint8_t size); bool zexist(const char *str, uint8_t size); char * strcat_zchar(char * dest, char * name, uint8_t size, const char *defaultName, uint8_t defaultNameSize, uint8_t defaultIdx); #define strcat_modelname(dest, idx) strcat_zchar(dest, modelHeaders[idx].name, LEN_MODEL_NAME, STR_MODEL, PSIZE(TR_MODEL), idx+1) -#define strcat_phasename(dest, idx) strcat_zchar(dest, g_model.phaseData[idx].name, LEN_FP_NAME, NULL, 0, 0) -#define strcat_mixername(dest, idx) strcat_zchar(dest, g_model.mixData[idx].name, LEN_EXPOMIX_NAME, NULL, 0, 0) +#define strcat_phasename(dest, idx) strcat_zchar(dest, g_model.phaseData[idx].name, LEN_FP_NAME, STR_FP, PSIZE(TR_FP), idx+1) #define ZLEN(s) zlen(s, sizeof(s)) #define ZEXIST(s) zexist(s, sizeof(s)) #endif diff --git a/radio/src/simpgmspace.cpp b/radio/src/simpgmspace.cpp index cd3fb4803..0b5deb589 100644 --- a/radio/src/simpgmspace.cpp +++ b/radio/src/simpgmspace.cpp @@ -300,7 +300,7 @@ void *main_thread(void *) eeReadAll(); // load general setup and selected model #if defined(CPUARM) && defined(SDCARD) - refreshSystemAudioFiles(); + referenceSystemAudioFiles(); #endif if (g_eeGeneral.backlightMode != e_backlight_mode_off) backlightOn(); // on Tx start turn the light on @@ -473,9 +473,10 @@ char *convertSimuPath(const char *path) FRESULT f_stat (const TCHAR * name, FILINFO *) { + char *path = convertSimuPath(name); struct stat tmp; - // printf("f_stat(%s)\n", path); fflush(stdout); - return stat(convertSimuPath(name), &tmp) ? FR_INVALID_NAME : FR_OK; + TRACE("f_stat(%s)", path); + return stat(path, &tmp) ? FR_INVALID_NAME : FR_OK; } FRESULT f_mount (BYTE, FATFS*) diff --git a/radio/src/targets/sky9x/diskio.cpp b/radio/src/targets/sky9x/diskio.cpp index d7f60e900..8d9ff5cfc 100644 --- a/radio/src/targets/sky9x/diskio.cpp +++ b/radio/src/targets/sky9x/diskio.cpp @@ -1014,7 +1014,7 @@ void sdMountPoll() case SD_ST_DATA: if (!usbPlugged() && f_mount(0, &g_FATFS_Obj) == FR_OK) { - refreshSystemAudioFiles(); + referenceSystemAudioFiles(); Card_state = SD_ST_MOUNTED; } break; @@ -1082,7 +1082,7 @@ void sdInit() Card_state = SD_ST_DATA; if (f_mount(0, &g_FATFS_Obj) == FR_OK) { - refreshSystemAudioFiles(); + referenceSystemAudioFiles(); Card_state = SD_ST_MOUNTED; } diff --git a/radio/src/targets/taranis/diskio.cpp b/radio/src/targets/taranis/diskio.cpp index b1d2dea7e..d9586804f 100644 --- a/radio/src/targets/taranis/diskio.cpp +++ b/radio/src/targets/taranis/diskio.cpp @@ -969,7 +969,7 @@ FIL g_telemetryFile = {0}; void sdInit() { if (f_mount(0, &g_FATFS_Obj) == FR_OK) { - refreshSystemAudioFiles(); + referenceSystemAudioFiles(); #if defined(DEBUG) f_open(&g_telemetryFile, LOGS_PATH "/sport.log", FA_OPEN_ALWAYS | FA_WRITE); From ad134173be5e70692d31bc99e0f56b4786906e1f Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Wed, 19 Feb 2014 11:30:54 +0100 Subject: [PATCH 14/89] Issue #713 - Now automatic Switch files are played --- radio/src/audio_arm.cpp | 10 ++++++ radio/src/audio_arm.h | 7 ++-- radio/src/opentx.cpp | 77 +++++++++++++++++++++++++++++++---------- 3 files changed, 73 insertions(+), 21 deletions(-) diff --git a/radio/src/audio_arm.cpp b/radio/src/audio_arm.cpp index ea4af817c..0dc92a1e3 100644 --- a/radio/src/audio_arm.cpp +++ b/radio/src/audio_arm.cpp @@ -296,8 +296,18 @@ bool isAudioFileReferenced(uint32_t i, char * filename) return false; } + +void playModelEvent(uint8_t category, uint8_t index, uint8_t event) +{ + char filename[AUDIO_FILENAME_MAXLEN+1]; + if (isAudioFileReferenced((category << 24) + (index << 16) + event, filename)) { + audioQueue.playFile(filename); + } +} #else + #define isAudioFileReferenced(i, f) false + #endif // TODO should be generated and in flash rather than in ram diff --git a/radio/src/audio_arm.h b/radio/src/audio_arm.h index b96808426..41a170d7b 100644 --- a/radio/src/audio_arm.h +++ b/radio/src/audio_arm.h @@ -305,11 +305,14 @@ void pushPrompt(uint16_t prompt, uint8_t id=0); #define AUDIO_RESET() audioQueue.reset() #if defined(SDCARD) - #define PLAY_PHASE_OFF(phase) do { char filename[AUDIO_FILENAME_MAXLEN+1]; if (isAudioFileReferenced((PHASE_AUDIO_CATEGORY << 24) + (phase << 16) + AUDIO_EVENT_OFF, filename)) audioQueue.playFile(filename); } while (0) - #define PLAY_PHASE_ON(phase) do { char filename[AUDIO_FILENAME_MAXLEN+1]; if (isAudioFileReferenced((PHASE_AUDIO_CATEGORY << 24) + (phase << 16) + AUDIO_EVENT_ON, filename)) audioQueue.playFile(filename); } while (0) + void playModelEvent(uint8_t category, uint8_t index, uint8_t event=0); + #define PLAY_PHASE_OFF(phase) playModelEvent(PHASE_AUDIO_CATEGORY, phase, AUDIO_EVENT_OFF) + #define PLAY_PHASE_ON(phase) playModelEvent(PHASE_AUDIO_CATEGORY, phase, AUDIO_EVENT_ON) + #define PLAY_SWITCH_MOVED(sw) playModelEvent(SWITCH_AUDIO_CATEGORY, sw) #else #define PLAY_PHASE_OFF(phase) #define PLAY_PHASE_ON(phase) + #define PLAY_SWITCH_MOVED(sw) #endif void referenceSystemAudioFiles(); diff --git a/radio/src/opentx.cpp b/radio/src/opentx.cpp index 320421007..49d8c94ff 100644 --- a/radio/src/opentx.cpp +++ b/radio/src/opentx.cpp @@ -1322,26 +1322,65 @@ tmr10ms_t switchesMidposStart[6] = { 0 }; uint32_t switchesPos = 0; tmr10ms_t potsLastposStart[NUM_XPOTS]; uint8_t potsPos[NUM_XPOTS]; + +uint32_t check2PosSwitchPosition(EnumKeys sw) +{ + uint32_t result; + uint32_t index; + + if (switchState(sw)) + index = sw - SW_SA0; + else + index = sw - SW_SA0 + 1; + + result = (1 << index); + + if (!(switchesPos & result)) { + PLAY_SWITCH_MOVED(index); + } + + return result; +} + #define DELAY_SWITCH_3POS 10/*100ms*/ -#define CHECK_2POS(sw) newPos |= (switchState(sw ## 0) ? (1 << (sw ## 0 - SW_SA0)) : (1 << (sw ## 0 - SW_SA0 + 1))) -#define CHECK_3POS(idx, sw) if (switchState(sw ## 0)) { \ - newPos |= (1 << (sw ## 0 - SW_SA0)); \ - switchesMidposStart[idx] = 0; \ - } \ - else if (switchState(sw ## 2)) { \ - newPos |= (1 << (sw ## 0 - SW_SA0 + 2)); \ - switchesMidposStart[idx] = 0; \ - } \ - else if ((switchesPos & (1 << (sw ## 0 - SW_SA0 + 1))) || (switchesMidposStart[idx] && (tmr10ms_t)(get_tmr10ms() - switchesMidposStart[idx]) > DELAY_SWITCH_3POS)) { \ - newPos |= (1 << (sw ## 0 - SW_SA0 + 1)); \ - switchesMidposStart[idx] = 0; \ - } \ - else { \ - if (!switchesMidposStart[idx]) { \ - switchesMidposStart[idx] = get_tmr10ms(); \ - } \ - newPos |= (switchesPos & (0x7 << (sw ## 0 - SW_SA0))); \ - } +uint32_t check3PosSwitchPosition(uint8_t idx, EnumKeys sw) +{ + uint32_t result; + uint32_t index; + + if (switchState(sw)) { + index = sw - SW_SA0; + result = (1 << index); + switchesMidposStart[idx] = 0; + } + else if (switchState(EnumKeys(sw+2))) { + index = sw - SW_SA0 + 2; + result = (1 << index); + switchesMidposStart[idx] = 0; + } + else if ((switchesPos & (1 << (sw - SW_SA0 + 1))) || (switchesMidposStart[idx] && (tmr10ms_t)(get_tmr10ms() - switchesMidposStart[idx]) > DELAY_SWITCH_3POS)) { + index = sw - SW_SA0 + 1; + result = (1 << index); + switchesMidposStart[idx] = 0; + } + else { + index = sw - SW_SA0 + 1; + if (!switchesMidposStart[idx]) { + switchesMidposStart[idx] = get_tmr10ms(); + } + result = (switchesPos & (0x7 << (sw - SW_SA0))); + } + + if (!(switchesPos & result)) { + PLAY_SWITCH_MOVED(index); + } + + return result; +} + +#define CHECK_2POS(sw) newPos |= check2PosSwitchPosition(sw ## 0) +#define CHECK_3POS(idx, sw) newPos |= check3PosSwitchPosition(idx, sw ## 0) + void getSwitchesPosition() { uint32_t newPos = 0; From 7c4214d5b9305cc9f713232cf36b63bb32b7aa94 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Wed, 19 Feb 2014 16:41:18 +0100 Subject: [PATCH 15/89] More custom scripts (7 instead of 3) --- companion/src/eeprominterface.h | 2 +- radio/src/.gitignore | 1 + radio/src/gui/menu_model.cpp | 6 +++--- radio/src/lua.cpp | 4 ++-- radio/src/myeeprom.h | 2 +- radio/src/sdcard.h | 1 - 6 files changed, 8 insertions(+), 8 deletions(-) diff --git a/companion/src/eeprominterface.h b/companion/src/eeprominterface.h index 14dc0d7ac..05d871592 100644 --- a/companion/src/eeprominterface.h +++ b/companion/src/eeprominterface.h @@ -856,7 +856,7 @@ class ModuleData { void clear() { memset(this, 0, sizeof(ModuleData)); } }; -#define C9X_MAX_SCRIPTS 3 +#define C9X_MAX_SCRIPTS 7 #define C9X_MAX_SCRIPT_INPUTS 10 class ScriptData { public: diff --git a/radio/src/.gitignore b/radio/src/.gitignore index 3a16d35fe..ecb3765ab 100644 --- a/radio/src/.gitignore +++ b/radio/src/.gitignore @@ -14,3 +14,4 @@ /SOUNDS /LOGS /*.bat +/TEMPLATES diff --git a/radio/src/gui/menu_model.cpp b/radio/src/gui/menu_model.cpp index 8d271aa56..9b79f61d9 100644 --- a/radio/src/gui/menu_model.cpp +++ b/radio/src/gui/menu_model.cpp @@ -5139,8 +5139,8 @@ void onModelCustomScriptMenu(const char *result) ScriptData &sd = g_model.scriptsData[s_currIdx]; if (result == STR_UPDATE_LIST) { - if (!listSdFiles(SCRIPTS_PATH, MIXES_EXT, sizeof(sd.file), NULL)) { - POPUP_WARNING(STR_NO_BITMAPS_ON_SD); + if (!listSdFiles(SCRIPTS_PATH, SCRIPTS_EXT, sizeof(sd.file), NULL)) { + POPUP_WARNING(STR_NO_SCRIPTS_ON_SD); s_menu_flags = 0; } } @@ -5187,7 +5187,7 @@ void menuModelCustomScriptOne(uint8_t event) lcd_putsiAtt(SCRIPT_ONE_2ND_COLUMN_POS, y, STR_VCSWFUNC, 0, attr); if (attr && event==EVT_KEY_BREAK(KEY_ENTER) && !READ_ONLY()) { s_editMode = 0; - if (listSdFiles(SCRIPTS_PATH, MIXES_EXT, sizeof(sd.file), sd.file, LIST_NONE_SD_FILE)) { + if (listSdFiles(SCRIPTS_PATH, SCRIPTS_EXT, sizeof(sd.file), sd.file, LIST_NONE_SD_FILE)) { menuHandler = onModelCustomScriptMenu; } else { diff --git a/radio/src/lua.cpp b/radio/src/lua.cpp index 0e18824fa..1a2ab9e1a 100644 --- a/radio/src/lua.cpp +++ b/radio/src/lua.cpp @@ -935,10 +935,10 @@ void luaLoadModelScript(uint8_t index) sid.state = SCRIPT_NOFILE; if (ZEXIST(sd.file)) { - char filename[sizeof(SCRIPTS_PATH)+sizeof(sd.file)+sizeof(MIXES_EXT)] = SCRIPTS_PATH "/"; + char filename[sizeof(SCRIPTS_PATH)+sizeof(sd.file)+sizeof(SCRIPTS_EXT)] = SCRIPTS_PATH "/"; strncpy(filename+sizeof(SCRIPTS_PATH), sd.file, sizeof(sd.file)); filename[sizeof(SCRIPTS_PATH)+sizeof(sd.file)] = '\0'; - strcat(filename+sizeof(SCRIPTS_PATH), MIXES_EXT); + strcat(filename+sizeof(SCRIPTS_PATH), SCRIPTS_EXT); luaLoad(filename, sid); } } diff --git a/radio/src/myeeprom.h b/radio/src/myeeprom.h index 0f2e0076b..bcfa22a20 100644 --- a/radio/src/myeeprom.h +++ b/radio/src/myeeprom.h @@ -75,7 +75,7 @@ #define MAX_EXPOS 64 #define NUM_CSW 32 // number of custom switches #define NUM_CFN 64 // number of functions assigned to switches - #define MAX_SCRIPTS 3 + #define MAX_SCRIPTS 7 #define MAX_INPUTS 32 #elif defined(CPUARM) #define MAX_MODELS 60 diff --git a/radio/src/sdcard.h b/radio/src/sdcard.h index 4e6c446d7..07e528a68 100644 --- a/radio/src/sdcard.h +++ b/radio/src/sdcard.h @@ -53,7 +53,6 @@ #define SOUNDS_EXT ".wav" #define BITMAPS_EXT ".bmp" #define SCRIPTS_EXT ".lua" -#define MIXES_EXT ".mix" #define TEXT_EXT ".txt" extern FATFS g_FATFS_Obj; From b3e2e8e32128b53ee6ca39dbd9aae15070119c21 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Wed, 19 Feb 2014 16:57:02 +0100 Subject: [PATCH 16/89] Compilation failure. Thanks Jenkins! --- radio/src/gui/menus.cpp | 4 ++-- radio/src/myeeprom.h | 3 ++- 2 files changed, 4 insertions(+), 3 deletions(-) diff --git a/radio/src/gui/menus.cpp b/radio/src/gui/menus.cpp index b760f3e22..dfc74980e 100644 --- a/radio/src/gui/menus.cpp +++ b/radio/src/gui/menus.cpp @@ -778,7 +778,7 @@ bool check(check_event_t event, uint8_t curr, const MenuFuncP *menuTab, uint8_t vertpos_t realPgOfs = s_pgOfs; vertpos_t realMaxrow = maxrow; for (vertpos_t i=1; i<=maxrow; i++) { - if (MAXCOL_RAW(i) == HIDDEN_ROW) { + if (MAXCOL(i) == HIDDEN_ROW) { realMaxrow--; if (i < l_posVert) realPosVert--; @@ -790,7 +790,7 @@ bool check(check_event_t event, uint8_t curr, const MenuFuncP *menuTab, uint8_t else if (realPosVert<1+realPgOfs) realPgOfs = realPosVert-1; s_pgOfs = realPgOfs; for (vertpos_t i=1; i<=realPgOfs; i++) { - if (MAXCOL_RAW(i) == HIDDEN_ROW) { + if (MAXCOL(i) == HIDDEN_ROW) { s_pgOfs++; } } diff --git a/radio/src/myeeprom.h b/radio/src/myeeprom.h index bcfa22a20..ab7073e18 100644 --- a/radio/src/myeeprom.h +++ b/radio/src/myeeprom.h @@ -323,8 +323,9 @@ enum BacklightMode { #define SPLASH_MODE uint8_t splashMode:1; uint8_t spare4:2 #endif -#if defined(PCBTARANIS) #define POTS_POS_COUNT 6 + +#if defined(PCBTARANIS) PACK(typedef struct { uint8_t count; uint8_t steps[POTS_POS_COUNT-1]; From 481e312ae3598b960415874f45eafc4c710e1651 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Wed, 19 Feb 2014 17:47:21 +0100 Subject: [PATCH 17/89] Vario part in Global Settings page reworked --- radio/src/gui/menu_general.cpp | 54 ++++++++++++++++++++-------------- radio/src/translations/en.h | 4 +-- 2 files changed, 34 insertions(+), 24 deletions(-) diff --git a/radio/src/gui/menu_general.cpp b/radio/src/gui/menu_general.cpp index 14669926a..e8bd44897 100644 --- a/radio/src/gui/menu_general.cpp +++ b/radio/src/gui/menu_general.cpp @@ -149,13 +149,14 @@ enum menuGeneralSetupItems { IF_VOICE(ITEM_SETUP_SPEAKER_VOLUME) IF_CPUARM(ITEM_SETUP_BEEP_VOLUME) IF_CPUARM(ITEM_SETUP_WAV_VOLUME) + IF_CPUARM(ITEM_SETUP_BACKGROUND_VOLUME) + ITEM_SETUP_BEEP_LENGTH, + IF_AUDIO(ITEM_SETUP_SPEAKER_PITCH) + IF_CPUARM(ITEM_SETUP_VARIO_LABEL) IF_CPUARM(ITEM_SETUP_VARIO_VOLUME) IF_CPUARM(ITEM_SETUP_VARIO_PITCH) IF_CPUARM(ITEM_SETUP_VARIO_RANGE) IF_CPUARM(ITEM_SETUP_VARIO_REPEAT) - IF_CPUARM(ITEM_SETUP_BACKGROUND_VOLUME) - ITEM_SETUP_BEEP_LENGTH, - IF_AUDIO(ITEM_SETUP_SPEAKER_PITCH) IF_HAPTIC(ITEM_SETUP_HAPTIC_LABEL) IF_HAPTIC(ITEM_SETUP_HAPTIC_MODE) IF_HAPTIC(ITEM_SETUP_HAPTIC_LENGTH) @@ -214,7 +215,7 @@ void menuGeneralSetup(uint8_t event) } #endif - MENU(STR_MENURADIOSETUP, menuTabDiag, e_Setup, ITEM_SETUP_MAX+1, {0, IF_RTCLOCK(2) IF_RTCLOCK(2) IF_BATTGRAPH(1) LABEL(SOUND), IF_AUDIO(0) IF_BUZZER(0) IF_VOICE(0) IF_CPUARM(0) IF_CPUARM(0) IF_CPUARM(0) IF_CPUARM(0) IF_CPUARM(0) IF_CPUARM(0) IF_CPUARM(0) 0, IF_AUDIO(0) IF_HAPTIC(LABEL(HAPTIC)) IF_HAPTIC(0) IF_HAPTIC(0) IF_HAPTIC(0) 0, LABEL(ALARMS), 0, CASE_PCBSKY9X(0) CASE_PCBSKY9X(0) 0, 0, 0, IF_ROTARY_ENCODERS(0) LABEL(BACKLIGHT), 0, 0, IF_CPUARM(0) CASE_PWM_BACKLIGHT(0) CASE_PWM_BACKLIGHT(0) 0, IF_SPLASH(0) IF_GPS(0) IF_GPS(0) IF_PXX(0) IF_CPUARM(0) IF_CPUARM(0) IF_FAI_CHOICE(0) 0, LABEL(TX_MODE), CASE_PCBTARANIS(0) 1/*to force edit mode*/}); + MENU(STR_MENURADIOSETUP, menuTabDiag, e_Setup, ITEM_SETUP_MAX+1, {0, IF_RTCLOCK(2) IF_RTCLOCK(2) IF_BATTGRAPH(1) LABEL(SOUND), IF_AUDIO(0) IF_BUZZER(0) IF_VOICE(0) IF_CPUARM(0) IF_CPUARM(0) IF_CPUARM(0) 0, IF_AUDIO(0) IF_CPUARM(LABEL(VARIO)) IF_CPUARM(0) IF_CPUARM(0) IF_CPUARM(0) IF_CPUARM(0) IF_HAPTIC(LABEL(HAPTIC)) IF_HAPTIC(0) IF_HAPTIC(0) IF_HAPTIC(0) 0, LABEL(ALARMS), 0, CASE_PCBSKY9X(0) CASE_PCBSKY9X(0) 0, 0, 0, IF_ROTARY_ENCODERS(0) LABEL(BACKLIGHT), 0, 0, IF_CPUARM(0) CASE_PWM_BACKLIGHT(0) CASE_PWM_BACKLIGHT(0) 0, IF_SPLASH(0) IF_GPS(0) IF_GPS(0) IF_PXX(0) IF_CPUARM(0) IF_CPUARM(0) IF_FAI_CHOICE(0) 0, LABEL(TX_MODE), CASE_PCBTARANIS(0) 1/*to force edit mode*/}); uint8_t sub = m_posVert - 1; @@ -360,24 +361,6 @@ void menuGeneralSetup(uint8_t event) case ITEM_SETUP_WAV_VOLUME: SLIDER_5POS(y, g_eeGeneral.wavVolume, STR_WAV_VOLUME, event, attr); break; - case ITEM_SETUP_VARIO_VOLUME: - SLIDER_5POS(y, g_eeGeneral.varioVolume, STR_VARIO_VOLUME, event, attr); - break; - case ITEM_SETUP_VARIO_PITCH: - lcd_putsLeft(y, "\001Vario Pitch"); - lcd_outdezAtt(RADIO_SETUP_2ND_COLUMN, y, VARIO_FREQUENCY_ZERO+(g_eeGeneral.varioPitch*10), attr|LEFT); - if (attr) CHECK_INCDEC_GENVAR(event, g_eeGeneral.varioPitch, -40, 40); - break; - case ITEM_SETUP_VARIO_RANGE: - lcd_putsLeft(y, "\001Vario Max"); - lcd_outdezAtt(RADIO_SETUP_2ND_COLUMN, y, VARIO_FREQUENCY_ZERO+(g_eeGeneral.varioPitch*10)+VARIO_FREQUENCY_RANGE+(g_eeGeneral.varioRange*10), attr|LEFT); - if (attr) CHECK_INCDEC_GENVAR(event, g_eeGeneral.varioRange, -80, 80); - break; - case ITEM_SETUP_VARIO_REPEAT: - lcd_putsLeft(y, "\001Vario Repeat"); - lcd_outdezAtt(RADIO_SETUP_2ND_COLUMN, y, VARIO_REPEAT_ZERO+(g_eeGeneral.varioRepeat*10), attr|LEFT); - if (attr) CHECK_INCDEC_GENVAR(event, g_eeGeneral.varioRepeat, -30, 120); - break; case ITEM_SETUP_BACKGROUND_VOLUME: SLIDER_5POS(y, g_eeGeneral.backgroundVolume, STR_BG_VOLUME, event, attr); break; @@ -397,6 +380,33 @@ void menuGeneralSetup(uint8_t event) break; #endif +#if defined(CPUARM) + case ITEM_SETUP_VARIO_LABEL: + lcd_putsLeft(y, STR_VARIO); + break; + case ITEM_SETUP_VARIO_VOLUME: + SLIDER_5POS(y, g_eeGeneral.varioVolume, TR_SPEAKER_VOLUME, event, attr); + break; + case ITEM_SETUP_VARIO_PITCH: + lcd_putsLeft(y, "\001Pitch at Zero"); + lcd_outdezAtt(RADIO_SETUP_2ND_COLUMN, y, VARIO_FREQUENCY_ZERO+(g_eeGeneral.varioPitch*10), attr|LEFT); + lcd_putsAtt(lcdLastPos, y, "Hz", attr); + if (attr) CHECK_INCDEC_GENVAR(event, g_eeGeneral.varioPitch, -40, 40); + break; + case ITEM_SETUP_VARIO_RANGE: + lcd_putsLeft(y, "\001Pitch at Max"); + lcd_outdezAtt(RADIO_SETUP_2ND_COLUMN, y, VARIO_FREQUENCY_ZERO+(g_eeGeneral.varioPitch*10)+VARIO_FREQUENCY_RANGE+(g_eeGeneral.varioRange*10), attr|LEFT); + lcd_putsAtt(lcdLastPos, y, "Hz", attr); + if (attr) CHECK_INCDEC_GENVAR(event, g_eeGeneral.varioRange, -80, 80); + break; + case ITEM_SETUP_VARIO_REPEAT: + lcd_putsLeft(y, "\001Repeat at Zero"); + lcd_outdezAtt(RADIO_SETUP_2ND_COLUMN, y, VARIO_REPEAT_ZERO+(g_eeGeneral.varioRepeat*10), attr|LEFT); + lcd_putsAtt(lcdLastPos, y, "ms", attr); + if (attr) CHECK_INCDEC_GENVAR(event, g_eeGeneral.varioRepeat, -30, 50); + break; +#endif + #if defined(HAPTIC) case ITEM_SETUP_HAPTIC_LABEL: lcd_putsLeft(y, STR_HAPTIC_LABEL); diff --git a/radio/src/translations/en.h b/radio/src/translations/en.h index 1d1fcd108..898f94080 100644 --- a/radio/src/translations/en.h +++ b/radio/src/translations/en.h @@ -614,7 +614,7 @@ #define TR_ALARMSWARN "ALARMS" #define TR_SWITCHWARN TR("SWITCH","CONTROL") #define TR_INVERT_THR TR("Invert Thr?","Invert Throttle?") -#define TR_SPEAKER_VOLUME INDENT "Volume" +#define TR_SPEAKER_VOLUME INDENT "Volume" // TODO could be TR_VOLUME ? #define TR_LCD "LCD" #define TR_BRIGHTNESS INDENT "Brightness" #define TR_CPU_TEMP "CPU Temp.\016>" @@ -791,7 +791,7 @@ #define TR_BEEP_VOLUME "Beep Volume" #define TR_WAV_VOLUME "Wav Volume" -#define TR_VARIO_VOLUME "Vario Volume" +#define TR_VARIO_VOLUME "Vario Volume" // TODO may be removed #define TR_BG_VOLUME "Bg Volume" #define TR_TOP_BAR "Top Bar" From 4d1df6a166e9dee91d66a408680f476e62fbdc16 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Wed, 19 Feb 2014 20:31:50 +0100 Subject: [PATCH 18/89] 4 stages mixer. Now vario can be used with a background music! --- radio/src/audio_arm.cpp | 166 +++++++++++++++++++--------------------- radio/src/audio_arm.h | 70 +++++++++-------- radio/src/maths.cpp | 10 +-- 3 files changed, 123 insertions(+), 123 deletions(-) diff --git a/radio/src/audio_arm.cpp b/radio/src/audio_arm.cpp index 4c374dc73..c93597304 100644 --- a/radio/src/audio_arm.cpp +++ b/radio/src/audio_arm.cpp @@ -435,7 +435,7 @@ void AudioQueue::pushBuffer(AudioBuffer *buffer) __enable_irq(); } -void mix(uint16_t * result, int sample, unsigned int fade) +void mixSample(uint16_t * result, int sample, unsigned int fade) { *result = limit(0, *result + ((sample >> fade) >> 4), 4095); } @@ -445,42 +445,41 @@ void mix(uint16_t * result, int sample, unsigned int fade) #define RIFF_CHUNK_SIZE 12 uint8_t wavBuffer[AUDIO_BUFFER_SIZE*2]; -int AudioQueue::mixWav(AudioContext &context, AudioBuffer *buffer, int volume, unsigned int fade) +int WavContext::mixBuffer(AudioBuffer *buffer, int volume, unsigned int fade) { FRESULT result = FR_OK; UINT read = 0; - AudioFragment & fragment = context.fragment; if (fragment.file[1]) { - result = f_open(&context.wav.file, fragment.file, FA_OPEN_EXISTING | FA_READ); + result = f_open(&state.file, fragment.file, FA_OPEN_EXISTING | FA_READ); fragment.file[1] = 0; if (result == FR_OK) { - result = f_read(&context.wav.file, wavBuffer, RIFF_CHUNK_SIZE+8, &read); + result = f_read(&state.file, wavBuffer, RIFF_CHUNK_SIZE+8, &read); if (result == FR_OK && read == RIFF_CHUNK_SIZE+8 && !memcmp(wavBuffer, "RIFF", 4) && !memcmp(wavBuffer+8, "WAVEfmt ", 8)) { uint32_t size = *((uint32_t *)(wavBuffer+16)); - result = (size < 256 ? f_read(&context.wav.file, wavBuffer, size+8, &read) : FR_DENIED); + result = (size < 256 ? f_read(&state.file, wavBuffer, size+8, &read) : FR_DENIED); if (result == FR_OK && read == size+8) { - context.wav.codec = ((uint16_t *)wavBuffer)[0]; - context.wav.freq = ((uint16_t *)wavBuffer)[2]; + state.codec = ((uint16_t *)wavBuffer)[0]; + state.freq = ((uint16_t *)wavBuffer)[2]; uint32_t *wavSamplesPtr = (uint32_t *)(wavBuffer + size); uint32_t size = wavSamplesPtr[1]; - if (context.wav.freq != 0 && context.wav.freq * (AUDIO_SAMPLE_RATE / context.wav.freq) == AUDIO_SAMPLE_RATE) { - context.wav.resampleRatio = (AUDIO_SAMPLE_RATE / context.wav.freq); - context.wav.readSize = (context.wav.codec == CODEC_ID_PCM_S16LE ? 2*AUDIO_BUFFER_SIZE : AUDIO_BUFFER_SIZE) / context.wav.resampleRatio; + if (state.freq != 0 && state.freq * (AUDIO_SAMPLE_RATE / state.freq) == AUDIO_SAMPLE_RATE) { + state.resampleRatio = (AUDIO_SAMPLE_RATE / state.freq); + state.readSize = (state.codec == CODEC_ID_PCM_S16LE ? 2*AUDIO_BUFFER_SIZE : AUDIO_BUFFER_SIZE) / state.resampleRatio; } else { result = FR_DENIED; } while (result == FR_OK && memcmp(wavSamplesPtr, "data", 4) != 0) { - result = f_lseek(&context.wav.file, f_tell(&context.wav.file)+size); + result = f_lseek(&state.file, f_tell(&state.file)+size); if (result == FR_OK) { - result = f_read(&context.wav.file, wavBuffer, 8, &read); + result = f_read(&state.file, wavBuffer, 8, &read); if (read != 8) result = FR_DENIED; wavSamplesPtr = (uint32_t *)wavBuffer; size = wavSamplesPtr[1]; } } - context.wav.size = size; + state.size = size; } else { result = FR_DENIED; @@ -494,46 +493,46 @@ int AudioQueue::mixWav(AudioContext &context, AudioBuffer *buffer, int volume, u read = 0; if (result == FR_OK) { - result = f_read(&context.wav.file, wavBuffer, context.wav.readSize, &read); + result = f_read(&state.file, wavBuffer, state.readSize, &read); if (result == FR_OK) { - if (read > context.wav.size) { - read = context.wav.size; + if (read > state.size) { + read = state.size; } - context.wav.size -= read; + state.size -= read; - if (read != context.wav.readSize) { - f_close(&context.wav.file); + if (read != state.readSize) { + f_close(&state.file); fragment.clear(); } uint16_t * samples = buffer->data; - if (context.wav.codec == CODEC_ID_PCM_S16LE) { + if (state.codec == CODEC_ID_PCM_S16LE) { read /= 2; for (uint32_t i=0; idata; } } - context.clear(); + clear(); return -result; } #else -int AudioQueue::mixWav(AudioContext &context, AudioBuffer *buffer, int volume, unsigned int fade) +int WavContext::mixBuffer(AudioBuffer *buffer, int volume, unsigned int fade) { return 0; } @@ -549,26 +548,25 @@ inline float evalVolumeRatio(int freq, int volume) return result; } -int AudioQueue::mixTone(AudioContext &context, AudioBuffer *buffer, int volume, unsigned int fade) +int ToneContext::mixBuffer(AudioBuffer *buffer, int volume, unsigned int fade) { - AudioFragment & fragment = context.fragment; int duration = 0; int result = 0; - int remainingDuration = fragment.tone.duration - context.tone.duration; + int remainingDuration = fragment.tone.duration - state.duration; if (remainingDuration > 0) { int points; - double toneIdx = context.tone.idx; + double toneIdx = state.idx; if (fragment.tone.reset) { - context.tone.duration = 0; - context.tone.pause = 0; + state.duration = 0; + state.pause = 0; } - if (fragment.tone.freq != context.tone.freq) { - context.tone.freq = fragment.tone.freq; - context.tone.step = double(DIM(sineValues)*fragment.tone.freq) / AUDIO_SAMPLE_RATE; - context.tone.volume = evalVolumeRatio(fragment.tone.freq, volume); + if (fragment.tone.freq != state.freq) { + state.freq = fragment.tone.freq; + state.step = double(DIM(sineValues)*fragment.tone.freq) / AUDIO_SAMPLE_RATE; + state.volume = evalVolumeRatio(fragment.tone.freq, volume); } if (fragment.tone.freqIncr) { @@ -582,59 +580,41 @@ int AudioQueue::mixTone(AudioContext &context, AudioBuffer *buffer, int volume, else { duration = remainingDuration; points = (duration * AUDIO_BUFFER_SIZE) / AUDIO_BUFFER_DURATION; - unsigned int end = toneIdx + (context.tone.step * points); + unsigned int end = toneIdx + (state.step * points); if (end > DIM(sineValues)) end -= (end % DIM(sineValues)); else end = DIM(sineValues); - points = (double(end) - toneIdx) / context.tone.step; + points = (double(end) - toneIdx) / state.step; } for (int i=0; idata[i], sample, fade); - toneIdx += context.tone.step; + int16_t sample = sineValues[int(toneIdx)] / state.volume; + mixSample(&buffer->data[i], sample, fade); + toneIdx += state.step; if ((unsigned int)toneIdx >= DIM(sineValues)) toneIdx -= DIM(sineValues); } if (remainingDuration > AUDIO_BUFFER_DURATION) { - context.tone.duration += AUDIO_BUFFER_DURATION; - context.tone.idx = toneIdx; + state.duration += AUDIO_BUFFER_DURATION; + state.idx = toneIdx; return AUDIO_BUFFER_SIZE; } else { - context.tone.duration = 32000; // once the tone is finished, it's not possible to update its frequency and duration + state.duration = 32000; // once the tone is finished, it's not possible to update its frequency and duration } } - remainingDuration = fragment.tone.pause - context.tone.pause; + remainingDuration = fragment.tone.pause - state.pause; if (remainingDuration > 0) { result = AUDIO_BUFFER_SIZE; - context.tone.pause += min(AUDIO_BUFFER_DURATION-duration, fragment.tone.pause); - if (fragment.tone.pause > context.tone.pause) + state.pause += min(AUDIO_BUFFER_DURATION-duration, fragment.tone.pause); + if (fragment.tone.pause > state.pause) return result; } - context.clear(); - return result; -} - -int AudioQueue::mixAudioContext(AudioContext &context, AudioBuffer *buffer, int beepVolume, int wavVolume, unsigned int fade) -{ - int result; - AudioFragment & fragment = context.fragment; - - if (fragment.type == FRAGMENT_TONE) { - result = mixTone(context, buffer, beepVolume, fade); - } - else if (fragment.type == FRAGMENT_FILE) { - result = mixWav(context, buffer, wavVolume, fade); - } - else { - result = 0; - } - + clear(); return result; } @@ -651,15 +631,20 @@ void AudioQueue::wakeup() buffer->data[i] = 0x8000 >> 4; /* silence */ } - // mix the foreground context - result = mixAudioContext(foregroundContext, buffer, g_eeGeneral.beepVolume, g_eeGeneral.wavVolume, fade); + // mix the priority context (only tones) + result = priorityContext.mixBuffer(buffer, g_eeGeneral.beepVolume, fade); if (result > 0) { size = result; fade += 1; } - // mix the normal context - result = mixAudioContext(currentContext, buffer, g_eeGeneral.beepVolume, g_eeGeneral.wavVolume, fade); + // mix the normal context (tones and wavs) + if (normalContext.fragment.type == FRAGMENT_TONE) + result = normalContext.tone.mixBuffer(buffer, g_eeGeneral.beepVolume, fade); + else if (normalContext.fragment.type == FRAGMENT_FILE) + result = normalContext.wav.mixBuffer(buffer, g_eeGeneral.wavVolume, fade); + else + result = 0; if (result > 0) { size = max(size, result); fade += 1; @@ -667,8 +652,7 @@ void AudioQueue::wakeup() else { CoEnterMutexSection(audioMutex); if (ridx != widx) { - currentContext.clear(); - currentContext.fragment = fragments[ridx]; + normalContext.fragment = fragments[ridx]; if (!fragments[ridx].repeat--) { ridx = (ridx + 1) % AUDIO_QUEUE_LENGTH; } @@ -676,9 +660,16 @@ void AudioQueue::wakeup() CoLeaveMutexSection(audioMutex); } + // mix the vario context + result = varioContext.mixBuffer(buffer, g_eeGeneral.varioVolume, fade); + if (result > 0) { + size = max(size, result); + fade += 1; + } + // mix the background context if (!isFunctionActive(FUNCTION_BACKGND_MUSIC_PAUSE)) { - result = mixAudioContext(backgroundContext, buffer, g_eeGeneral.varioVolume, g_eeGeneral.backgroundVolume, fade); + result = backgroundContext.mixBuffer(buffer, g_eeGeneral.backgroundVolume, fade); if (result > 0) { size = max(size, result); } @@ -711,7 +702,7 @@ void AudioQueue::pause(uint16_t len) bool AudioQueue::isPlaying(uint8_t id) { - if (currentContext.fragment.id == id || backgroundContext.fragment.id == id) + if (normalContext.fragment.id == id || backgroundContext.fragment.id == id) return true; uint8_t i = ridx; @@ -732,9 +723,7 @@ void AudioQueue::playTone(uint16_t freq, uint16_t len, uint16_t pause, uint8_t f freq = BEEP_MIN_FREQ; if (flags & PLAY_BACKGROUND) { - AudioFragment & fragment = backgroundContext.fragment; - if (fragment.type != FRAGMENT_TONE) - backgroundContext.clear(); + AudioFragment & fragment = varioContext.fragment; fragment.type = FRAGMENT_TONE; fragment.tone.freq = freq; fragment.tone.duration = len; @@ -746,9 +735,9 @@ void AudioQueue::playTone(uint16_t freq, uint16_t len, uint16_t pause, uint8_t f len = getToneLength(len); if (flags & PLAY_NOW) { - AudioFragment & fragment = foregroundContext.fragment; + AudioFragment & fragment = priorityContext.fragment; if (fragment.type == FRAGMENT_EMPTY) { - foregroundContext.clear(); + priorityContext.clear(); fragment.type = FRAGMENT_TONE; fragment.repeat = flags & 0x0f; fragment.tone.freq = freq; @@ -805,9 +794,9 @@ void AudioQueue::playFile(const char *filename, uint8_t flags, uint8_t id) fragment.id = id; } else if (flags & PLAY_NOW) { - AudioFragment & fragment = foregroundContext.fragment; + AudioFragment & fragment = priorityContext.fragment; if (fragment.type == FRAGMENT_EMPTY) { - foregroundContext.clear(); + priorityContext.clear(); fragment.type = FRAGMENT_FILE; strcpy(fragment.file, filename); fragment.repeat = flags & 0x0f; @@ -857,8 +846,9 @@ void AudioQueue::reset() { CoEnterMutexSection(audioMutex); widx = ridx; // clean the queue - foregroundContext.clear(); - currentContext.clear(); + priorityContext.clear(); + normalContext.tone.clear(); + varioContext.clear(); backgroundContext.clear(); CoLeaveMutexSection(audioMutex); } diff --git a/radio/src/audio_arm.h b/radio/src/audio_arm.h index 40be7179a..14dbc666a 100644 --- a/radio/src/audio_arm.h +++ b/radio/src/audio_arm.h @@ -90,21 +90,10 @@ struct AudioFragment { } }; -class AudioContext { +class ToneContext { public: AudioFragment fragment; -#if defined(SDCARD) - struct { - FIL file; - uint8_t codec; - uint32_t freq; - uint32_t size; - uint8_t resampleRatio; - uint16_t readSize; - } wav; -#endif - struct { double step; double idx; @@ -112,22 +101,46 @@ class AudioContext { uint16_t freq; uint16_t duration; uint16_t pause; - inline void clear() - { - step = 0; - idx = 0; - volume = 0; - freq = 0; - duration = 0; - pause = 0; - } - } tone; + } state; + + inline void clear() + { + memset(this, 0, sizeof(ToneContext)); + } + + int mixBuffer(AudioBuffer *buffer, int volume, unsigned int fade); +}; + +class WavContext { + public: + AudioFragment fragment; + + struct { + FIL file; + uint8_t codec; + uint32_t freq; + uint32_t size; + uint8_t resampleRatio; + uint16_t readSize; + } state; inline void clear() { fragment.clear(); - tone.clear(); } + + int mixBuffer(AudioBuffer *buffer, int volume, unsigned int fade); +}; + +class MixedContext { + public: + union { + AudioFragment fragment; + ToneContext tone; + WavContext wav; + }; + + int mixBuffer(AudioBuffer *buffer, int volume, unsigned int fade); }; bool dacQueue(AudioBuffer *buffer); @@ -190,19 +203,16 @@ class AudioQueue { void wakeup(); - int mixAudioContext(AudioContext &context, AudioBuffer *buffer, int beepVolume, int wavVolume, unsigned int fade); - int mixTone(AudioContext &context, AudioBuffer *buffer, int volume, unsigned int fade); - int mixWav(AudioContext &context, AudioBuffer *buffer, int volume, unsigned int fade); - volatile bool state; uint8_t ridx; uint8_t widx; AudioFragment fragments[AUDIO_QUEUE_LENGTH]; - AudioContext backgroundContext; // for background music / vario - AudioContext currentContext; - AudioContext foregroundContext; // for important beeps + MixedContext normalContext; + WavContext backgroundContext; + ToneContext priorityContext; + ToneContext varioContext; AudioBuffer buffers[AUDIO_BUFFER_COUNT]; uint8_t bufferRIdx; diff --git a/radio/src/maths.cpp b/radio/src/maths.cpp index 67456c95d..e05877fbe 100644 --- a/radio/src/maths.cpp +++ b/radio/src/maths.cpp @@ -140,18 +140,18 @@ void varioWakeup() verticalSpeed = varioMin; if (verticalSpeed > varioCenterMin) { - varioFreq = VARIO_FREQUENCY_ZERO + (g_eeGeneral.varioPitch*10) + (((VARIO_FREQUENCY_RANGE+(g_eeGeneral.varioRange*10)) * verticalSpeed) / varioMax); - int varioPeriod = VARIO_REPEAT_MAX + ((VARIO_REPEAT_ZERO+(g_eeGeneral.varioRepeat*10)-VARIO_REPEAT_MAX) * (varioMax-verticalSpeed) * (varioMax-verticalSpeed)) / (varioMax * varioMax); + varioFreq = VARIO_FREQUENCY_ZERO + (g_eeGeneral.varioPitch*10) + (((VARIO_FREQUENCY_RANGE+(g_eeGeneral.varioRange*10)) * (verticalSpeed-varioCenterMin)) / varioMax); + int varioPeriod = VARIO_REPEAT_MAX + ((VARIO_REPEAT_ZERO+(g_eeGeneral.varioRepeat*10)-VARIO_REPEAT_MAX) * (varioMax-verticalSpeed) * (varioMax-verticalSpeed)) / ((varioMax-varioCenterMin) * (varioMax-varioCenterMin)); if (verticalSpeed >= varioCenterMax || varioCenterMin == varioCenterMax) - varioDuration = varioPeriod / 4; + varioDuration = varioPeriod / 5; else varioDuration = varioPeriod * (85 - (((verticalSpeed-varioCenterMin) * 25) / (varioCenterMax-varioCenterMin))) / 100; varioPause = varioPeriod - varioDuration; varioFlags = PLAY_BACKGROUND; } else { - varioFreq = VARIO_FREQUENCY_ZERO + (g_eeGeneral.varioPitch*10) - (((VARIO_FREQUENCY_ZERO+(g_eeGeneral.varioPitch*10)-BEEP_MIN_FREQ) * verticalSpeed) / varioMin); - varioDuration = 80; // TODO 20 // continuous beep: we will enter again here before the tone ends + varioFreq = VARIO_FREQUENCY_ZERO + (g_eeGeneral.varioPitch*10) - (((VARIO_FREQUENCY_ZERO+(g_eeGeneral.varioPitch*10)-((VARIO_FREQUENCY_ZERO + (g_eeGeneral.varioPitch*10))/2)) * (verticalSpeed-varioCenterMin)) / varioMin); + varioDuration = 80; // continuous beep: we will enter again here before the tone ends varioFlags = PLAY_BACKGROUND|PLAY_NOW; } From 82348f7e059571432e193e1b124eb8604d5c3b1a Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Wed, 19 Feb 2014 21:39:39 +0100 Subject: [PATCH 19/89] Import/Export broken in Companion (7scripts instead of 3) --- companion/src/firmwares/opentx/opentxeeprom.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/companion/src/firmwares/opentx/opentxeeprom.cpp b/companion/src/firmwares/opentx/opentxeeprom.cpp index c078e6009..3b3259803 100644 --- a/companion/src/firmwares/opentx/opentxeeprom.cpp +++ b/companion/src/firmwares/opentx/opentxeeprom.cpp @@ -2205,7 +2205,7 @@ Open9xModelDataNew::Open9xModelDataNew(ModelData & modelData, BoardEnum board, u } if (IS_TARANIS(board) && version >= 216) { - for (int i=0; i<3; i++) { + for (int i=0; i<7; i++) { ScriptData & script = modelData.scriptData[i]; internalField.Append(new ZCharField<10>(script.filename)); internalField.Append(new ZCharField<10>(script.name)); From 7e0a30c08fc302608d45b63813fab67507eb2639 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Thu, 20 Feb 2014 16:21:04 +0100 Subject: [PATCH 20/89] Reduces the duration of SD search for automatic model files --- radio/src/audio_arm.cpp | 115 +++++++++++++++++++++++----------------- 1 file changed, 67 insertions(+), 48 deletions(-) diff --git a/radio/src/audio_arm.cpp b/radio/src/audio_arm.cpp index 0dc92a1e3..4161778d8 100644 --- a/radio/src/audio_arm.cpp +++ b/radio/src/audio_arm.cpp @@ -163,12 +163,18 @@ void referenceSystemAudioFiles() const char * suffixes[] = { "-off", "-on" }; +char * getModelPath(char * path) +{ + strcpy(path, SOUNDS_PATH "/"); + strncpy(path+SOUNDS_PATH_LNG_OFS, currentLanguagePack->id, 2); + char * result = strcat_modelname(path+sizeof(SOUNDS_PATH), g_eeGeneral.currModel); + *result++ = '/'; + return result; +} + void getPhaseAudioFile(char * filename, int index, unsigned int event) { - strcpy(filename, SOUNDS_PATH "/"); - strncpy(filename+SOUNDS_PATH_LNG_OFS, currentLanguagePack->id, 2); - char *str = strcat_modelname(filename+sizeof(SOUNDS_PATH), g_eeGeneral.currModel); - *str++ = '/'; + char * str = getModelPath(filename); char * tmp = strcat_phasename(str, index); strcpy(tmp, suffixes[event]); strcat(tmp, SOUNDS_EXT); @@ -176,10 +182,7 @@ void getPhaseAudioFile(char * filename, int index, unsigned int event) void getSwitchAudioFile(char * filename, int index) { - strcpy(filename, SOUNDS_PATH "/"); - strncpy(filename+SOUNDS_PATH_LNG_OFS, currentLanguagePack->id, 2); - char *str = strcat_modelname(filename+sizeof(SOUNDS_PATH), g_eeGeneral.currModel); - *str++ = '/'; + char * str = getModelPath(filename); int len = STR_VSWITCHES[0]; strncpy(str, &STR_VSWITCHES[1+len*index], len); str += len-1; @@ -203,10 +206,7 @@ void getSwitchAudioFile(char * filename, int index) void getLogicalSwitchAudioFile(char * filename, int index, unsigned int event) { - strcpy(filename, SOUNDS_PATH "/"); - strncpy(filename+SOUNDS_PATH_LNG_OFS, currentLanguagePack->id, 2); - char *str = strcat_modelname(filename+sizeof(SOUNDS_PATH), g_eeGeneral.currModel); - *str++ = '/'; + char * str = getModelPath(filename); int len = STR_VSWITCHES[0]; strncpy(str, &STR_VSWITCHES[1+len*(index+SWSRC_FIRST_CSW-1)], len); str += len; @@ -216,46 +216,65 @@ void getLogicalSwitchAudioFile(char * filename, int index, unsigned int event) void referenceModelAudioFiles() { - char filename[AUDIO_FILENAME_MAXLEN+1]; + char path[AUDIO_FILENAME_MAXLEN+1]; + FILINFO fno; + DIR dir; + char *fn; /* This function is assuming non-Unicode cfg. */ + TCHAR lfn[_MAX_LFN + 1]; + fno.lfname = lfn; + fno.lfsize = sizeof(lfn); - { - // Phases Audio Files -[on|off].wav - uint32_t mask = 0; - for (int i=0; i-[on|off].wav + for (int i=0; i-[up|mid|down].wav + for (int i=0; i-[on|off].wav + for (int i=0; i-[up|mid|down].wav - uint32_t mask = 0; - for (int i=0; i-[on|off].wav - uint64_t mask = 0; - for (int i=0; i Date: Thu, 20 Feb 2014 16:51:25 +0100 Subject: [PATCH 21/89] Now the Ele stick can be used for tests when vario source is dTE --- radio/src/maths.cpp | 14 ++++++++------ 1 file changed, 8 insertions(+), 6 deletions(-) diff --git a/radio/src/maths.cpp b/radio/src/maths.cpp index e05877fbe..570669b9a 100644 --- a/radio/src/maths.cpp +++ b/radio/src/maths.cpp @@ -122,12 +122,14 @@ void varioWakeup() int varioFreq, varioDuration, varioPause=0; uint8_t varioFlags; -#if 1 - #warning "Ele stick for vario tests" - int verticalSpeed = getValue(MIXSRC_Ele); -#else - int verticalSpeed = frskyData.hub.varioSpeed; -#endif + int verticalSpeed; + if (g_model.frsky.varioSource == VARIO_SOURCE_DTE) { + #warning "Ele stick for vario tests" + verticalSpeed = getValue(MIXSRC_Ele); + } + else { + verticalSpeed = frskyData.hub.varioSpeed; + } int varioCenterMin = (int)g_model.frsky.varioCenterMin * 10 - 50; int varioCenterMax = (int)g_model.frsky.varioCenterMax * 10 + 50; From d5348de16e4ab18a9b091d40b25d0251ecb57e07 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Thu, 20 Feb 2014 16:57:36 +0100 Subject: [PATCH 22/89] All alerts are TADA :) --- radio/src/audio_arm.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/radio/src/audio_arm.cpp b/radio/src/audio_arm.cpp index 4161778d8..7942b6e5f 100644 --- a/radio/src/audio_arm.cpp +++ b/radio/src/audio_arm.cpp @@ -289,7 +289,7 @@ bool isAudioFileReferenced(uint32_t i, char * filename) #endif if (category == SYSTEM_AUDIO_CATEGORY) { - if (sdAvailableSystemAudioFiles & MASK_SYSTEM_AUDIO_FILE(index)) { + if (sdAvailableSystemAudioFiles & MASK_SYSTEM_AUDIO_FILE(event)) { getSystemAudioFile(filename, index); return true; } From 1f318844f06874f3174ed1b5aa254bce442f45c4 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Thu, 20 Feb 2014 17:01:34 +0100 Subject: [PATCH 23/89] Compilation error (thanks Jenkins) --- radio/src/maths.cpp | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/radio/src/maths.cpp b/radio/src/maths.cpp index 570669b9a..1b87e4437 100644 --- a/radio/src/maths.cpp +++ b/radio/src/maths.cpp @@ -122,14 +122,14 @@ void varioWakeup() int varioFreq, varioDuration, varioPause=0; uint8_t varioFlags; - int verticalSpeed; + int verticalSpeed = frskyData.hub.varioSpeed; + +#if defined(PCBTARANIS) if (g_model.frsky.varioSource == VARIO_SOURCE_DTE) { #warning "Ele stick for vario tests" verticalSpeed = getValue(MIXSRC_Ele); } - else { - verticalSpeed = frskyData.hub.varioSpeed; - } +#endif int varioCenterMin = (int)g_model.frsky.varioCenterMin * 10 - 50; int varioCenterMax = (int)g_model.frsky.varioCenterMax * 10 + 50; From 444fc8571044f1f1500c1f85eabe5f7251db85ef Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Thu, 20 Feb 2014 16:57:36 +0100 Subject: [PATCH 24/89] All alerts are TADA :) --- radio/src/audio_arm.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/radio/src/audio_arm.cpp b/radio/src/audio_arm.cpp index 4161778d8..1b95e8281 100644 --- a/radio/src/audio_arm.cpp +++ b/radio/src/audio_arm.cpp @@ -267,7 +267,7 @@ void referenceModelAudioFiles() for (int i=0; i Date: Thu, 20 Feb 2014 18:00:14 +0100 Subject: [PATCH 25/89] Again the TADA on all alerts --- radio/src/audio_arm.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/radio/src/audio_arm.cpp b/radio/src/audio_arm.cpp index eb87d20b9..2f6636203 100644 --- a/radio/src/audio_arm.cpp +++ b/radio/src/audio_arm.cpp @@ -290,7 +290,7 @@ bool isAudioFileReferenced(uint32_t i, char * filename) if (category == SYSTEM_AUDIO_CATEGORY) { if (sdAvailableSystemAudioFiles & MASK_SYSTEM_AUDIO_FILE(event)) { - getSystemAudioFile(filename, index); + getSystemAudioFile(filename, event); return true; } } From a91bfbba9e6f28ed95671ac8d119afa2a0e0a3bd Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Thu, 20 Feb 2014 18:15:24 +0100 Subject: [PATCH 26/89] Bug in SD audio parse --- radio/src/audio_arm.cpp | 2 ++ 1 file changed, 2 insertions(+) diff --git a/radio/src/audio_arm.cpp b/radio/src/audio_arm.cpp index 2f6636203..977774357 100644 --- a/radio/src/audio_arm.cpp +++ b/radio/src/audio_arm.cpp @@ -169,6 +169,7 @@ char * getModelPath(char * path) strncpy(path+SOUNDS_PATH_LNG_OFS, currentLanguagePack->id, 2); char * result = strcat_modelname(path+sizeof(SOUNDS_PATH), g_eeGeneral.currModel); *result++ = '/'; + *result = '\0'; return result; } @@ -229,6 +230,7 @@ void referenceModelAudioFiles() sdAvailableLogicalSwitchAudioFiles = 0; char * filename = getModelPath(path); +// TODO au cas ou ... *(filename-1) = '\0'; FRESULT res = f_opendir(&dir, path); /* Open the directory */ if (res == FR_OK) { From 91bec1e4d967a96927a97cfd987e1ac11de91a7c Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Thu, 20 Feb 2014 19:07:39 +0100 Subject: [PATCH 27/89] Now it works. No hashed sounds at startup. --- radio/src/audio_arm.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/radio/src/audio_arm.cpp b/radio/src/audio_arm.cpp index 977774357..7f1d92d52 100644 --- a/radio/src/audio_arm.cpp +++ b/radio/src/audio_arm.cpp @@ -230,7 +230,7 @@ void referenceModelAudioFiles() sdAvailableLogicalSwitchAudioFiles = 0; char * filename = getModelPath(path); -// TODO au cas ou ... *(filename-1) = '\0'; + *(filename-1) = '\0'; FRESULT res = f_opendir(&dir, path); /* Open the directory */ if (res == FR_OK) { From 65e6814b2851a7fd809529832f4a94c8eabd7426 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Thu, 20 Feb 2014 19:25:08 +0100 Subject: [PATCH 28/89] Switches positions not played at startup --- radio/src/opentx.cpp | 32 ++++++++++++++++++++------------ 1 file changed, 20 insertions(+), 12 deletions(-) diff --git a/radio/src/opentx.cpp b/radio/src/opentx.cpp index 49d8c94ff..a086d8764 100644 --- a/radio/src/opentx.cpp +++ b/radio/src/opentx.cpp @@ -1323,7 +1323,7 @@ uint32_t switchesPos = 0; tmr10ms_t potsLastposStart[NUM_XPOTS]; uint8_t potsPos[NUM_XPOTS]; -uint32_t check2PosSwitchPosition(EnumKeys sw) +uint32_t check2PosSwitchPosition(EnumKeys sw, bool play) { uint32_t result; uint32_t index; @@ -1335,7 +1335,7 @@ uint32_t check2PosSwitchPosition(EnumKeys sw) result = (1 << index); - if (!(switchesPos & result)) { + if (play && !(switchesPos & result)) { PLAY_SWITCH_MOVED(index); } @@ -1343,7 +1343,7 @@ uint32_t check2PosSwitchPosition(EnumKeys sw) } #define DELAY_SWITCH_3POS 10/*100ms*/ -uint32_t check3PosSwitchPosition(uint8_t idx, EnumKeys sw) +uint32_t check3PosSwitchPosition(uint8_t idx, EnumKeys sw, bool play) { uint32_t result; uint32_t index; @@ -1371,17 +1371,17 @@ uint32_t check3PosSwitchPosition(uint8_t idx, EnumKeys sw) result = (switchesPos & (0x7 << (sw - SW_SA0))); } - if (!(switchesPos & result)) { + if (play && !(switchesPos & result)) { PLAY_SWITCH_MOVED(index); } return result; } -#define CHECK_2POS(sw) newPos |= check2PosSwitchPosition(sw ## 0) -#define CHECK_3POS(idx, sw) newPos |= check3PosSwitchPosition(idx, sw ## 0) +#define CHECK_2POS(sw) newPos |= check2PosSwitchPosition(sw ## 0, play) +#define CHECK_3POS(idx, sw) newPos |= check3PosSwitchPosition(idx, sw ## 0, play) -void getSwitchesPosition() +void getSwitchesPosition(bool play) { uint32_t newPos = 0; CHECK_3POS(0, SW_SA); @@ -1415,7 +1415,7 @@ void getSwitchesPosition() #define SWITCH_POSITION(sw) (switchesPos & (1<<(sw))) #define POT_POSITION(sw) ((potsPos[(sw)/POTS_POS_COUNT] & 0x0f) == ((sw) % POTS_POS_COUNT)) #else -#define getSwitchesPosition() +#define getSwitchesPosition(...) #define SWITCH_POSITION(idx) switchState((EnumKeys)(SW_BASE+(idx))) #endif @@ -3903,17 +3903,25 @@ void doMixerCalculations() PORTH |= 0x40; // PORTH:6 LOW->HIGH signals start of mixer interrupt #endif - static tmr10ms_t lastTMR; + static tmr10ms_t lastTMR = 0; tmr10ms_t tmr10ms = get_tmr10ms(); - uint8_t tick10ms = (tmr10ms >= lastTMR ? tmr10ms - lastTMR : 1); // handle tick10ms overrun - //@@@ open.20.fsguruh: correct overflow handling costs a lot of code; happens only each 11 min; + uint8_t tick10ms = (tmr10ms >= lastTMR ? tmr10ms - lastTMR : 1); + // handle tick10ms overrun + // correct overflow handling costs a lot of code; happens only each 11 min; // therefore forget the exact calculation and use only 1 instead; good compromise + +#if !defined(CPUARM) lastTMR = tmr10ms; +#endif getADC(); - getSwitchesPosition(); + getSwitchesPosition(lastTMR != 0); + +#if defined(CPUARM) + lastTMR = tmr10ms; +#endif #if defined(PCBSKY9X) && !defined(REVA) && !defined(SIMU) Current_analogue = (Current_analogue*31 + s_anaFilt[8] ) >> 5 ; From e5f336fba1c3f775fc5919cfee5c51f56955082c Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Thu, 20 Feb 2014 19:33:09 +0100 Subject: [PATCH 29/89] Indentation --- radio/src/opentx.cpp | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/radio/src/opentx.cpp b/radio/src/opentx.cpp index a086d8764..ff8a7c1d8 100644 --- a/radio/src/opentx.cpp +++ b/radio/src/opentx.cpp @@ -2419,8 +2419,8 @@ void checkSwitches() case 1: lcd_putc(60+i*(5*FW)+2*FW+2, 6*FH-2, g_model.potPosition[i] > (getValue(MIXSRC_FIRST_POT+i) >> 3) ? 126 : 127); break; - case 2: - case 3: + case 2: + case 3: lcd_putc(60+i*(5*FW)+2*FW+2, 6*FH-2, g_model.potPosition[i] > (getValue(MIXSRC_FIRST_POT+i) >> 3) ? '\300' : '\301'); break; } @@ -2438,11 +2438,11 @@ void checkSwitches() for (uint8_t i=0; i0?(i+3):(states&0x3)+1), attr); + attr = (states & (1 << (i+1))) == (switches_states & (1 << (i+1))) ? 0 : INVERS; + if (!(g_model.nSwToWarn & (1<0?(i+3):(states&0x3)+1), attr); x += 3*FW+FW/2; } #endif From f2f9579b77763026c815042bd6ab7e2d00819a46 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Thu, 20 Feb 2014 19:51:32 +0100 Subject: [PATCH 30/89] Automatic sounds for multipos switches --- radio/src/audio_arm.h | 6 +++--- radio/src/opentx.cpp | 8 ++++++-- 2 files changed, 9 insertions(+), 5 deletions(-) diff --git a/radio/src/audio_arm.h b/radio/src/audio_arm.h index 41a170d7b..8c67fad5e 100644 --- a/radio/src/audio_arm.h +++ b/radio/src/audio_arm.h @@ -306,9 +306,9 @@ void pushPrompt(uint16_t prompt, uint8_t id=0); #if defined(SDCARD) void playModelEvent(uint8_t category, uint8_t index, uint8_t event=0); - #define PLAY_PHASE_OFF(phase) playModelEvent(PHASE_AUDIO_CATEGORY, phase, AUDIO_EVENT_OFF) - #define PLAY_PHASE_ON(phase) playModelEvent(PHASE_AUDIO_CATEGORY, phase, AUDIO_EVENT_ON) - #define PLAY_SWITCH_MOVED(sw) playModelEvent(SWITCH_AUDIO_CATEGORY, sw) + #define PLAY_PHASE_OFF(phase) playModelEvent(PHASE_AUDIO_CATEGORY, phase, AUDIO_EVENT_OFF) + #define PLAY_PHASE_ON(phase) playModelEvent(PHASE_AUDIO_CATEGORY, phase, AUDIO_EVENT_ON) + #define PLAY_SWITCH_MOVED(sw) playModelEvent(SWITCH_AUDIO_CATEGORY, sw) #else #define PLAY_PHASE_OFF(phase) #define PLAY_PHASE_ON(phase) diff --git a/radio/src/opentx.cpp b/radio/src/opentx.cpp index ff8a7c1d8..7955f57b4 100644 --- a/radio/src/opentx.cpp +++ b/radio/src/opentx.cpp @@ -1400,13 +1400,17 @@ void getSwitchesPosition(bool play) if (calib->count>0 && calib->countcount); uint8_t previousPos = potsPos[i] >> 4; + uint8_t previousStoredPos = potsPos[i] & 0x0F; if (pos != previousPos) { potsLastposStart[i] = get_tmr10ms(); - potsPos[i] = (pos << 4) | (potsPos[i] & 0x0f); + potsPos[i] = (pos << 4) | previousStoredPos; } else if ((tmr10ms_t)(get_tmr10ms() - potsLastposStart[i]) > DELAY_SWITCH_3POS) { potsLastposStart[i] = 0; - potsPos[i] = (pos << 4) | (pos); + potsPos[i] = (pos << 4) | pos; + if (play && previousStoredPos != pos) { + PLAY_SWITCH_MOVED(SWSRC_LAST_SWITCH+i*POTS_POS_COUNT+pos); + } } } } From 901c5339ff55b799922e2345decb724c245a8ab1 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Thu, 20 Feb 2014 22:47:14 +0100 Subject: [PATCH 31/89] 1000bytes RAM saved --- radio/src/audio_arm.cpp | 51 ++--------------------------------------- radio/util/codecs.py | 51 +++++++++++++++++++++++++++++++++++++++++ 2 files changed, 53 insertions(+), 49 deletions(-) create mode 100644 radio/util/codecs.py diff --git a/radio/src/audio_arm.cpp b/radio/src/audio_arm.cpp index c93597304..ee7ef7d01 100644 --- a/radio/src/audio_arm.cpp +++ b/radio/src/audio_arm.cpp @@ -330,54 +330,8 @@ bool isAudioFileAvailable(uint32_t i, char * filename) #define isAudioFileAvailable(i, f) false #endif -int16_t alawTable[256]; -int16_t ulawTable[256]; - -#define SIGN_BIT (0x80) /* Sign bit for a A-law byte. */ -#define QUANT_MASK (0xf) /* Quantization field mask. */ -#define SEG_SHIFT (4) /* Left shift for segment number. */ -#define SEG_MASK (0x70) /* Segment field mask. */ -#define BIAS (0x84) /* Bias for linear code. */ - -static short alaw2linear(unsigned char a_val) -{ - int t; - int seg; - - a_val ^= 0x55; - - t = a_val & QUANT_MASK; - seg = ((unsigned)a_val & SEG_MASK) >> SEG_SHIFT; - if(seg) t= (t + t + 1 + 32) << (seg + 2); - else t= (t + t + 1 ) << 3; - - return (a_val & SIGN_BIT) ? t : -t; -} - -static short ulaw2linear(unsigned char u_val) -{ - int t; - - /* Complement to obtain normal u-law value. */ - u_val = ~u_val; - - /* - * Extract and bias the quantization bits. Then - * shift up by the segment number and subtract out the bias. - */ - t = ((u_val & QUANT_MASK) << 3) + BIAS; - t <<= ((unsigned)u_val & SEG_MASK) >> SEG_SHIFT; - - return (u_val & SIGN_BIT) ? (BIAS - t) : (t - BIAS); -} - -void codecsInit() -{ - for (uint32_t i=0; i<256; i++) { - alawTable[i] = alaw2linear(i); - ulawTable[i] = ulaw2linear(i); - } -} +const int16_t alawTable[256] = { -5504, -5248, -6016, -5760, -4480, -4224, -4992, -4736, -7552, -7296, -8064, -7808, -6528, -6272, -7040, -6784, -2752, -2624, -3008, -2880, -2240, -2112, -2496, -2368, -3776, -3648, -4032, -3904, -3264, -3136, -3520, -3392, -22016, -20992, -24064, -23040, -17920, -16896, -19968, -18944, -30208, -29184, -32256, -31232, -26112, -25088, -28160, -27136, -11008, -10496, -12032, -11520, -8960, -8448, -9984, -9472, -15104, -14592, -16128, -15616, -13056, -12544, -14080, -13568, -344, -328, -376, -360, -280, -264, -312, -296, -472, -456, -504, -488, -408, -392, -440, -424, -88, -72, -120, -104, -24, -8, -56, -40, -216, -200, -248, -232, -152, -136, -184, -168, -1376, -1312, -1504, -1440, -1120, -1056, -1248, -1184, -1888, -1824, -2016, -1952, -1632, -1568, -1760, -1696, -688, -656, -752, -720, -560, -528, -624, -592, -944, -912, -1008, -976, -816, -784, -880, -848, 5504, 5248, 6016, 5760, 4480, 4224, 4992, 4736, 7552, 7296, 8064, 7808, 6528, 6272, 7040, 6784, 2752, 2624, 3008, 2880, 2240, 2112, 2496, 2368, 3776, 3648, 4032, 3904, 3264, 3136, 3520, 3392, 22016, 20992, 24064, 23040, 17920, 16896, 19968, 18944, 30208, 29184, 32256, 31232, 26112, 25088, 28160, 27136, 11008, 10496, 12032, 11520, 8960, 8448, 9984, 9472, 15104, 14592, 16128, 15616, 13056, 12544, 14080, 13568, 344, 328, 376, 360, 280, 264, 312, 296, 472, 456, 504, 488, 408, 392, 440, 424, 88, 72, 120, 104, 24, 8, 56, 40, 216, 200, 248, 232, 152, 136, 184, 168, 1376, 1312, 1504, 1440, 1120, 1056, 1248, 1184, 1888, 1824, 2016, 1952, 1632, 1568, 1760, 1696, 688, 656, 752, 720, 560, 528, 624, 592, 944, 912, 1008, 976, 816, 784, 880, 848 }; +const int16_t ulawTable[256] = { -32124, -31100, -30076, -29052, -28028, -27004, -25980, -24956, -23932, -22908, -21884, -20860, -19836, -18812, -17788, -16764, -15996, -15484, -14972, -14460, -13948, -13436, -12924, -12412, -11900, -11388, -10876, -10364, -9852, -9340, -8828, -8316, -7932, -7676, -7420, -7164, -6908, -6652, -6396, -6140, -5884, -5628, -5372, -5116, -4860, -4604, -4348, -4092, -3900, -3772, -3644, -3516, -3388, -3260, -3132, -3004, -2876, -2748, -2620, -2492, -2364, -2236, -2108, -1980, -1884, -1820, -1756, -1692, -1628, -1564, -1500, -1436, -1372, -1308, -1244, -1180, -1116, -1052, -988, -924, -876, -844, -812, -780, -748, -716, -684, -652, -620, -588, -556, -524, -492, -460, -428, -396, -372, -356, -340, -324, -308, -292, -276, -260, -244, -228, -212, -196, -180, -164, -148, -132, -120, -112, -104, -96, -88, -80, -72, -64, -56, -48, -40, -32, -24, -16, -8, 0, 32124, 31100, 30076, 29052, 28028, 27004, 25980, 24956, 23932, 22908, 21884, 20860, 19836, 18812, 17788, 16764, 15996, 15484, 14972, 14460, 13948, 13436, 12924, 12412, 11900, 11388, 10876, 10364, 9852, 9340, 8828, 8316, 7932, 7676, 7420, 7164, 6908, 6652, 6396, 6140, 5884, 5628, 5372, 5116, 4860, 4604, 4348, 4092, 3900, 3772, 3644, 3516, 3388, 3260, 3132, 3004, 2876, 2748, 2620, 2492, 2364, 2236, 2108, 1980, 1884, 1820, 1756, 1692, 1628, 1564, 1500, 1436, 1372, 1308, 1244, 1180, 1116, 1052, 988, 924, 876, 844, 812, 780, 748, 716, 684, 652, 620, 588, 556, 524, 492, 460, 428, 396, 372, 356, 340, 324, 308, 292, 276, 260, 244, 228, 212, 196, 180, 164, 148, 132, 120, 112, 104, 96, 88, 80, 72, 64, 56, 48, 40, 32, 24, 16, 8, 0 }; AudioQueue audioQueue; @@ -407,7 +361,6 @@ void audioTask(void* pdata) #if defined(SDCARD) if (!unexpectedShutdown) { - codecsInit(); sdInit(); AUDIO_TADA(); } diff --git a/radio/util/codecs.py b/radio/util/codecs.py new file mode 100644 index 000000000..4c75a6ed6 --- /dev/null +++ b/radio/util/codecs.py @@ -0,0 +1,51 @@ +#!/bin/env python + +SIGN_BIT = (0x80) # Sign bit for a A-law byte. +QUANT_MASK = (0xf) # Quantization field mask. +SEG_SHIFT = (4) # Left shift for segment number. +SEG_MASK = (0x70) # Segment field mask. +BIAS = (0x84) # Bias for linear code. + +def alaw2linear(a_val): + a_val ^= 0x55 + + t = a_val & QUANT_MASK + seg = (a_val & SEG_MASK) >> SEG_SHIFT + if (seg): + t = (t + t + 1 + 32) << (seg + 2) + else: + t = (t + t + 1 ) << 3 + + if a_val & SIGN_BIT: + return t + else: + return -t + +def ulaw2linear(u_val): + # Complement to obtain normal u-law value. + u_val = ~u_val + + # Extract and bias the quantization bits. Then + # shift up by the segment number and subtract out the bias. + t = ((u_val & QUANT_MASK) << 3) + BIAS + t <<= (u_val & SEG_MASK) >> SEG_SHIFT + + if u_val & SIGN_BIT: + return (BIAS - t) + else: + return (t - BIAS) + +def pcmTable(fn): + result = [] + for i in range(256): + result.append(fn(i)) + return result + +def tableToString(name, table): + result = 'const int16_t ' + name + '[256] = { ' + result += ', '.join([str(i) for i in table]) + result += ' };' + return result + +print tableToString('alawTable', pcmTable(alaw2linear)) +print tableToString('ulawTable', pcmTable(ulaw2linear)) From 99e42ceeb24d45909c1f2cade17bacf5aed30f32 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Thu, 20 Feb 2014 23:26:34 +0100 Subject: [PATCH 32/89] Different harmonics. Seem to be better. I would say that: - all beeps from the radio need to be lowered. - perhaps the low frequencies don't need to be amplified any more? --- radio/src/audio_arm.cpp | 206 ++++++++++++++++++++-------------------- radio/util/sinus.py | 2 +- 2 files changed, 104 insertions(+), 104 deletions(-) diff --git a/radio/src/audio_arm.cpp b/radio/src/audio_arm.cpp index ee7ef7d01..5e3fd7ef6 100644 --- a/radio/src/audio_arm.cpp +++ b/radio/src/audio_arm.cpp @@ -41,109 +41,109 @@ extern OS_MutexID audioMutex; const int16_t sineValues[] = { - 0, 218, 437, 655, 874, 1092, 1311, 1529, 1747, 1966, - 2184, 2401, 2619, 2837, 3054, 3271, 3488, 3705, 3921, 4138, - 4354, 4569, 4785, 5000, 5215, 5429, 5643, 5857, 6071, 6284, - 6496, 6709, 6920, 7132, 7343, 7553, 7763, 7973, 8182, 8390, - 8598, 8806, 9012, 9219, 9425, 9630, 9834, 10038, 10242, 10444, - 10646, 10848, 11049, 11249, 11448, 11647, 11845, 12042, 12238, 12434, - 12629, 12823, 13017, 13209, 13401, 13592, 13782, 13972, 14160, 14348, - 14535, 14721, 14906, 15090, 15273, 15456, 15637, 15818, 15997, 16176, - 16354, 16531, 16706, 16881, 17055, 17228, 17400, 17570, 17740, 17909, - 18077, 18243, 18409, 18574, 18737, 18899, 19061, 19221, 19380, 19538, - 19695, 19851, 20006, 20160, 20312, 20464, 20614, 20763, 20911, 21058, - 21204, 21348, 21491, 21634, 21775, 21914, 22053, 22191, 22327, 22462, - 22596, 22728, 22860, 22990, 23119, 23247, 23373, 23499, 23623, 23746, - 23867, 23988, 24107, 24225, 24342, 24457, 24571, 24684, 24796, 24906, - 25016, 25123, 25230, 25336, 25440, 25543, 25644, 25745, 25844, 25942, - 26039, 26134, 26228, 26321, 26412, 26503, 26592, 26680, 26766, 26852, - 26936, 27018, 27100, 27180, 27259, 27337, 27413, 27489, 27563, 27635, - 27707, 27777, 27846, 27914, 27980, 28046, 28110, 28173, 28234, 28295, - 28354, 28412, 28468, 28524, 28578, 28631, 28683, 28733, 28783, 28831, - 28878, 28924, 28968, 29011, 29054, 29095, 29134, 29173, 29210, 29247, - 29282, 29316, 29349, 29380, 29411, 29440, 29468, 29495, 29521, 29545, - 29569, 29591, 29613, 29633, 29652, 29670, 29686, 29702, 29717, 29730, - 29743, 29754, 29764, 29773, 29781, 29788, 29794, 29799, 29802, 29805, - 29806, 29807, 29806, 29805, 29802, 29799, 29794, 29788, 29781, 29773, - 29765, 29755, 29744, 29732, 29719, 29705, 29690, 29675, 29658, 29640, - 29621, 29601, 29580, 29559, 29536, 29512, 29488, 29462, 29435, 29408, - 29379, 29350, 29320, 29288, 29256, 29223, 29189, 29154, 29118, 29081, - 29044, 29005, 28966, 28925, 28884, 28842, 28799, 28755, 28710, 28664, - 28617, 28570, 28522, 28472, 28422, 28371, 28320, 28267, 28214, 28159, - 28104, 28048, 27991, 27934, 27875, 27816, 27756, 27695, 27633, 27570, - 27507, 27443, 27378, 27312, 27245, 27178, 27109, 27040, 26971, 26900, - 26829, 26756, 26683, 26610, 26535, 26460, 26384, 26307, 26229, 26151, - 26072, 25992, 25911, 25830, 25748, 25665, 25581, 25497, 25412, 25326, - 25239, 25152, 25064, 24975, 24885, 24795, 24704, 24612, 24520, 24427, - 24333, 24238, 24143, 24047, 23950, 23853, 23755, 23656, 23556, 23456, - 23355, 23254, 23151, 23048, 22945, 22840, 22735, 22630, 22523, 22416, - 22308, 22200, 22091, 21981, 21871, 21760, 21648, 21536, 21423, 21309, - 21194, 21079, 20964, 20848, 20731, 20613, 20495, 20376, 20257, 20137, - 20016, 19894, 19773, 19650, 19527, 19403, 19279, 19154, 19028, 18902, - 18775, 18647, 18519, 18391, 18262, 18132, 18001, 17870, 17739, 17607, - 17474, 17341, 17207, 17073, 16938, 16802, 16666, 16530, 16393, 16255, - 16117, 15978, 15839, 15699, 15559, 15418, 15277, 15135, 14992, 14850, - 14706, 14562, 14418, 14273, 14128, 13982, 13836, 13689, 13542, 13394, - 13246, 13097, 12948, 12799, 12649, 12498, 12347, 12196, 12044, 11892, - 11740, 11587, 11433, 11280, 11125, 10971, 10816, 10661, 10505, 10349, - 10192, 10036, 9878, 9721, 9563, 9405, 9246, 9087, 8928, 8768, - 8609, 8448, 8288, 8127, 7966, 7805, 7643, 7481, 7319, 7156, - 6994, 6831, 6667, 6504, 6340, 6176, 6012, 5847, 5683, 5518, - 5353, 5188, 5022, 4857, 4691, 4525, 4359, 4192, 4026, 3859, - 3692, 3526, 3358, 3191, 3024, 2857, 2689, 2521, 2354, 2186, - 2018, 1850, 1682, 1514, 1346, 1178, 1009, 841, 673, 505, - 336, 168, 0, -168, -336, -505, -673, -841, -1009, -1178, - -1346, -1514, -1682, -1850, -2018, -2186, -2354, -2521, -2689, -2857, - -3024, -3191, -3358, -3526, -3692, -3859, -4026, -4192, -4359, -4525, - -4691, -4857, -5022, -5188, -5353, -5518, -5683, -5847, -6012, -6176, - -6340, -6504, -6667, -6831, -6994, -7156, -7319, -7481, -7643, -7805, - -7966, -8127, -8288, -8448, -8609, -8768, -8928, -9087, -9246, -9405, - -9563, -9721, -9878, -10036, -10192, -10349, -10505, -10661, -10816, -10971, - -11125, -11280, -11433, -11587, -11740, -11892, -12044, -12196, -12347, -12498, - -12649, -12799, -12948, -13097, -13246, -13394, -13542, -13689, -13836, -13982, - -14128, -14273, -14418, -14562, -14706, -14850, -14992, -15135, -15277, -15418, - -15559, -15699, -15839, -15978, -16117, -16255, -16393, -16530, -16666, -16802, - -16938, -17073, -17207, -17341, -17474, -17607, -17739, -17870, -18001, -18132, - -18262, -18391, -18519, -18647, -18775, -18902, -19028, -19154, -19279, -19403, - -19527, -19650, -19773, -19894, -20016, -20137, -20257, -20376, -20495, -20613, - -20731, -20848, -20964, -21079, -21194, -21309, -21423, -21536, -21648, -21760, - -21871, -21981, -22091, -22200, -22308, -22416, -22523, -22630, -22735, -22840, - -22945, -23048, -23151, -23254, -23355, -23456, -23556, -23656, -23755, -23853, - -23950, -24047, -24143, -24238, -24333, -24427, -24520, -24612, -24704, -24795, - -24885, -24975, -25064, -25152, -25239, -25326, -25412, -25497, -25581, -25665, - -25748, -25830, -25911, -25992, -26072, -26151, -26229, -26307, -26384, -26460, - -26535, -26610, -26683, -26756, -26829, -26900, -26971, -27040, -27109, -27178, - -27245, -27312, -27378, -27443, -27507, -27570, -27633, -27695, -27756, -27816, - -27875, -27934, -27991, -28048, -28104, -28159, -28214, -28267, -28320, -28371, - -28422, -28472, -28522, -28570, -28617, -28664, -28710, -28755, -28799, -28842, - -28884, -28925, -28966, -29005, -29044, -29081, -29118, -29154, -29189, -29223, - -29256, -29288, -29320, -29350, -29379, -29408, -29435, -29462, -29488, -29512, - -29536, -29559, -29580, -29601, -29621, -29640, -29658, -29675, -29690, -29705, - -29719, -29732, -29744, -29755, -29765, -29773, -29781, -29788, -29794, -29799, - -29802, -29805, -29806, -29807, -29806, -29805, -29802, -29799, -29794, -29788, - -29781, -29773, -29764, -29754, -29743, -29730, -29717, -29702, -29686, -29670, - -29652, -29633, -29613, -29591, -29569, -29545, -29521, -29495, -29468, -29440, - -29411, -29380, -29349, -29316, -29282, -29247, -29210, -29173, -29134, -29095, - -29054, -29011, -28968, -28924, -28878, -28831, -28783, -28733, -28683, -28631, - -28578, -28524, -28468, -28412, -28354, -28295, -28234, -28173, -28110, -28046, - -27980, -27914, -27846, -27777, -27707, -27635, -27563, -27489, -27413, -27337, - -27259, -27180, -27100, -27018, -26936, -26852, -26766, -26680, -26592, -26503, - -26412, -26321, -26228, -26134, -26039, -25942, -25844, -25745, -25644, -25543, - -25440, -25336, -25230, -25123, -25016, -24906, -24796, -24684, -24571, -24457, - -24342, -24225, -24107, -23988, -23867, -23746, -23623, -23499, -23373, -23247, - -23119, -22990, -22860, -22728, -22596, -22462, -22327, -22191, -22053, -21914, - -21775, -21634, -21491, -21348, -21204, -21058, -20911, -20763, -20614, -20464, - -20312, -20160, -20006, -19851, -19695, -19538, -19380, -19221, -19061, -18899, - -18737, -18574, -18409, -18243, -18077, -17909, -17740, -17570, -17400, -17228, - -17055, -16881, -16706, -16531, -16354, -16176, -15997, -15818, -15637, -15456, - -15273, -15090, -14906, -14721, -14535, -14348, -14160, -13972, -13782, -13592, - -13401, -13209, -13017, -12823, -12629, -12434, -12238, -12042, -11845, -11647, - -11448, -11249, -11049, -10848, -10646, -10444, -10242, -10038, -9834, -9630, - -9425, -9219, -9012, -8806, -8598, -8390, -8182, -7973, -7763, -7553, - -7343, -7132, -6920, -6709, -6496, -6284, -6071, -5857, -5643, -5429, - -5215, -5000, -4785, -4569, -4354, -4138, -3921, -3705, -3488, -3271, - -3054, -2837, -2619, -2401, -2184, -1966, -1747, -1529, -1311, -1092, - -874, -655, -437, -218, + 0, 773, 1545, 2317, 3087, 3855, 4620, 5383, 6142, 6898, + 7649, 8395, 9135, 9870, 10599, 11321, 12035, 12742, 13441, 14132, + 14813, 15485, 16148, 16800, 17441, 18072, 18691, 19299, 19894, 20478, + 21048, 21605, 22149, 22680, 23196, 23698, 24185, 24658, 25116, 25558, + 25985, 26396, 26791, 27170, 27533, 27879, 28209, 28522, 28818, 29098, + 29360, 29605, 29833, 30044, 30237, 30414, 30573, 30714, 30839, 30946, + 31036, 31109, 31165, 31204, 31226, 31231, 31220, 31192, 31147, 31087, + 31011, 30918, 30811, 30687, 30549, 30396, 30227, 30045, 29848, 29637, + 29413, 29176, 28925, 28662, 28386, 28098, 27799, 27488, 27166, 26833, + 26491, 26138, 25776, 25404, 25024, 24636, 24240, 23836, 23425, 23007, + 22584, 22154, 21719, 21279, 20834, 20385, 19933, 19477, 19018, 18557, + 18094, 17630, 17164, 16698, 16231, 15764, 15298, 14834, 14370, 13908, + 13449, 12992, 12538, 12087, 11641, 11198, 10760, 10327, 9899, 9477, + 9060, 8650, 8247, 7850, 7460, 7079, 6704, 6338, 5981, 5632, + 5291, 4960, 4639, 4326, 4024, 3732, 3449, 3177, 2916, 2665, + 2425, 2196, 1978, 1771, 1575, 1391, 1218, 1056, 906, 767, + 640, 525, 421, 329, 248, 178, 121, 74, 39, 15, + 2, 0, 9, 29, 60, 101, 152, 214, 285, 367, + 458, 558, 668, 786, 914, 1050, 1194, 1346, 1506, 1674, + 1849, 2030, 2219, 2413, 2614, 2821, 3033, 3250, 3472, 3699, + 3929, 4164, 4402, 4644, 4888, 5135, 5384, 5635, 5887, 6141, + 6396, 6651, 6906, 7161, 7416, 7670, 7923, 8175, 8424, 8672, + 8917, 9160, 9399, 9635, 9868, 10097, 10321, 10541, 10757, 10967, + 11172, 11372, 11565, 11753, 11935, 12110, 12279, 12440, 12595, 12742, + 12882, 13014, 13139, 13255, 13364, 13464, 13556, 13640, 13715, 13781, + 13839, 13888, 13928, 13959, 13982, 13995, 14000, 13995, 13982, 13959, + 13928, 13888, 13839, 13781, 13715, 13640, 13556, 13464, 13364, 13255, + 13139, 13014, 12882, 12742, 12595, 12440, 12279, 12110, 11935, 11753, + 11565, 11372, 11172, 10967, 10757, 10541, 10321, 10097, 9868, 9635, + 9399, 9160, 8917, 8672, 8424, 8175, 7923, 7670, 7416, 7161, + 6906, 6651, 6396, 6141, 5887, 5635, 5384, 5135, 4888, 4644, + 4402, 4164, 3929, 3699, 3472, 3250, 3033, 2821, 2614, 2413, + 2219, 2030, 1849, 1674, 1506, 1346, 1194, 1050, 914, 786, + 668, 558, 458, 367, 285, 214, 152, 101, 60, 29, + 9, 0, 2, 15, 39, 74, 121, 178, 248, 329, + 421, 525, 640, 767, 906, 1056, 1218, 1391, 1575, 1771, + 1978, 2196, 2425, 2665, 2916, 3177, 3449, 3732, 4024, 4326, + 4639, 4960, 5291, 5632, 5981, 6338, 6704, 7079, 7460, 7850, + 8247, 8650, 9060, 9477, 9899, 10327, 10760, 11198, 11641, 12087, + 12538, 12992, 13449, 13908, 14370, 14834, 15298, 15764, 16231, 16698, + 17164, 17630, 18094, 18557, 19018, 19477, 19933, 20385, 20834, 21279, + 21719, 22154, 22584, 23007, 23425, 23836, 24240, 24636, 25024, 25404, + 25776, 26138, 26491, 26833, 27166, 27488, 27799, 28098, 28386, 28662, + 28925, 29176, 29413, 29637, 29848, 30045, 30227, 30396, 30549, 30687, + 30811, 30918, 31011, 31087, 31147, 31192, 31220, 31231, 31226, 31204, + 31165, 31109, 31036, 30946, 30839, 30714, 30573, 30414, 30237, 30044, + 29833, 29605, 29360, 29098, 28818, 28522, 28209, 27879, 27533, 27170, + 26791, 26396, 25985, 25558, 25116, 24658, 24185, 23698, 23196, 22680, + 22149, 21605, 21048, 20478, 19894, 19299, 18691, 18072, 17441, 16800, + 16148, 15485, 14813, 14132, 13441, 12742, 12035, 11321, 10599, 9870, + 9135, 8395, 7649, 6898, 6142, 5383, 4620, 3855, 3087, 2317, + 1545, 773, 0, -773, -1545, -2317, -3087, -3855, -4620, -5383, + -6142, -6898, -7649, -8395, -9135, -9870, -10599, -11321, -12035, -12742, + -13441, -14132, -14813, -15485, -16148, -16800, -17441, -18072, -18691, -19299, + -19894, -20478, -21048, -21605, -22149, -22680, -23196, -23698, -24185, -24658, + -25116, -25558, -25985, -26396, -26791, -27170, -27533, -27879, -28209, -28522, + -28818, -29098, -29360, -29605, -29833, -30044, -30237, -30414, -30573, -30714, + -30839, -30946, -31036, -31109, -31165, -31204, -31226, -31231, -31220, -31192, + -31147, -31087, -31011, -30918, -30811, -30687, -30549, -30396, -30227, -30045, + -29848, -29637, -29413, -29176, -28925, -28662, -28386, -28098, -27799, -27488, + -27166, -26833, -26491, -26138, -25776, -25404, -25024, -24636, -24240, -23836, + -23425, -23007, -22584, -22154, -21719, -21279, -20834, -20385, -19933, -19477, + -19018, -18557, -18094, -17630, -17164, -16698, -16231, -15764, -15298, -14834, + -14370, -13908, -13449, -12992, -12538, -12087, -11641, -11198, -10760, -10327, + -9899, -9477, -9060, -8650, -8247, -7850, -7460, -7079, -6704, -6338, + -5981, -5632, -5291, -4960, -4639, -4326, -4024, -3732, -3449, -3177, + -2916, -2665, -2425, -2196, -1978, -1771, -1575, -1391, -1218, -1056, + -906, -767, -640, -525, -421, -329, -248, -178, -121, -74, + -39, -15, -2, 0, -9, -29, -60, -101, -152, -214, + -285, -367, -458, -558, -668, -786, -914, -1050, -1194, -1346, + -1506, -1674, -1849, -2030, -2219, -2413, -2614, -2821, -3033, -3250, + -3472, -3699, -3929, -4164, -4402, -4644, -4888, -5135, -5384, -5635, + -5887, -6141, -6396, -6651, -6906, -7161, -7416, -7670, -7923, -8175, + -8424, -8672, -8917, -9160, -9399, -9635, -9868, -10097, -10321, -10541, + -10757, -10967, -11172, -11372, -11565, -11753, -11935, -12110, -12279, -12440, + -12595, -12742, -12882, -13014, -13139, -13255, -13364, -13464, -13556, -13640, + -13715, -13781, -13839, -13888, -13928, -13959, -13982, -13995, -14000, -13995, + -13982, -13959, -13928, -13888, -13839, -13781, -13715, -13640, -13556, -13464, + -13364, -13255, -13139, -13014, -12882, -12742, -12595, -12440, -12279, -12110, + -11935, -11753, -11565, -11372, -11172, -10967, -10757, -10541, -10321, -10097, + -9868, -9635, -9399, -9160, -8917, -8672, -8424, -8175, -7923, -7670, + -7416, -7161, -6906, -6651, -6396, -6141, -5887, -5635, -5384, -5135, + -4888, -4644, -4402, -4164, -3929, -3699, -3472, -3250, -3033, -2821, + -2614, -2413, -2219, -2030, -1849, -1674, -1506, -1346, -1194, -1050, + -914, -786, -668, -558, -458, -367, -285, -214, -152, -101, + -60, -29, -9, 0, -2, -15, -39, -74, -121, -178, + -248, -329, -421, -525, -640, -767, -906, -1056, -1218, -1391, + -1575, -1771, -1978, -2196, -2425, -2665, -2916, -3177, -3449, -3732, + -4024, -4326, -4639, -4960, -5291, -5632, -5981, -6338, -6704, -7079, + -7460, -7850, -8247, -8650, -9060, -9477, -9899, -10327, -10760, -11198, + -11641, -12087, -12538, -12992, -13449, -13908, -14370, -14834, -15298, -15764, + -16231, -16698, -17164, -17630, -18094, -18557, -19018, -19477, -19933, -20385, + -20834, -21279, -21719, -22154, -22584, -23007, -23425, -23836, -24240, -24636, + -25024, -25404, -25776, -26138, -26491, -26833, -27166, -27488, -27799, -28098, + -28386, -28662, -28925, -29176, -29413, -29637, -29848, -30045, -30227, -30396, + -30549, -30687, -30811, -30918, -31011, -31087, -31147, -31192, -31220, -31231, + -31226, -31204, -31165, -31109, -31036, -30946, -30839, -30714, -30573, -30414, + -30237, -30044, -29833, -29605, -29360, -29098, -28818, -28522, -28209, -27879, + -27533, -27170, -26791, -26396, -25985, -25558, -25116, -24658, -24185, -23698, + -23196, -22680, -22149, -21605, -21048, -20478, -19894, -19299, -18691, -18072, + -17441, -16800, -16148, -15485, -14813, -14132, -13441, -12742, -12035, -11321, + -10599, -9870, -9135, -8395, -7649, -6898, -6142, -5383, -4620, -3855, + -3087, -2317, -1545, -773, }; #if defined(SDCARD) diff --git a/radio/util/sinus.py b/radio/util/sinus.py index 68c09456d..cce2efce3 100644 --- a/radio/util/sinus.py +++ b/radio/util/sinus.py @@ -3,7 +3,7 @@ import math samples = 1024 -amplitudes = (60000, 4096, 1024) +amplitudes = (28000, 0, 28000, 0, 28000) for i in range(samples): sample = 0.0 From 6955a492d7fc9756f1d3ba8e301e29fcee5d8718 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Fri, 21 Feb 2014 11:52:02 +0100 Subject: [PATCH 33/89] A new set of amplitudes for the sine wave ... --- radio/src/audio_arm.cpp | 207 ++++++++++++++++++++-------------------- radio/util/sinus.py | 31 ++++-- 2 files changed, 126 insertions(+), 112 deletions(-) diff --git a/radio/src/audio_arm.cpp b/radio/src/audio_arm.cpp index 5e3fd7ef6..1340ccd7d 100644 --- a/radio/src/audio_arm.cpp +++ b/radio/src/audio_arm.cpp @@ -41,109 +41,110 @@ extern OS_MutexID audioMutex; const int16_t sineValues[] = { - 0, 773, 1545, 2317, 3087, 3855, 4620, 5383, 6142, 6898, - 7649, 8395, 9135, 9870, 10599, 11321, 12035, 12742, 13441, 14132, - 14813, 15485, 16148, 16800, 17441, 18072, 18691, 19299, 19894, 20478, - 21048, 21605, 22149, 22680, 23196, 23698, 24185, 24658, 25116, 25558, - 25985, 26396, 26791, 27170, 27533, 27879, 28209, 28522, 28818, 29098, - 29360, 29605, 29833, 30044, 30237, 30414, 30573, 30714, 30839, 30946, - 31036, 31109, 31165, 31204, 31226, 31231, 31220, 31192, 31147, 31087, - 31011, 30918, 30811, 30687, 30549, 30396, 30227, 30045, 29848, 29637, - 29413, 29176, 28925, 28662, 28386, 28098, 27799, 27488, 27166, 26833, - 26491, 26138, 25776, 25404, 25024, 24636, 24240, 23836, 23425, 23007, - 22584, 22154, 21719, 21279, 20834, 20385, 19933, 19477, 19018, 18557, - 18094, 17630, 17164, 16698, 16231, 15764, 15298, 14834, 14370, 13908, - 13449, 12992, 12538, 12087, 11641, 11198, 10760, 10327, 9899, 9477, - 9060, 8650, 8247, 7850, 7460, 7079, 6704, 6338, 5981, 5632, - 5291, 4960, 4639, 4326, 4024, 3732, 3449, 3177, 2916, 2665, - 2425, 2196, 1978, 1771, 1575, 1391, 1218, 1056, 906, 767, - 640, 525, 421, 329, 248, 178, 121, 74, 39, 15, - 2, 0, 9, 29, 60, 101, 152, 214, 285, 367, - 458, 558, 668, 786, 914, 1050, 1194, 1346, 1506, 1674, - 1849, 2030, 2219, 2413, 2614, 2821, 3033, 3250, 3472, 3699, - 3929, 4164, 4402, 4644, 4888, 5135, 5384, 5635, 5887, 6141, - 6396, 6651, 6906, 7161, 7416, 7670, 7923, 8175, 8424, 8672, - 8917, 9160, 9399, 9635, 9868, 10097, 10321, 10541, 10757, 10967, - 11172, 11372, 11565, 11753, 11935, 12110, 12279, 12440, 12595, 12742, - 12882, 13014, 13139, 13255, 13364, 13464, 13556, 13640, 13715, 13781, - 13839, 13888, 13928, 13959, 13982, 13995, 14000, 13995, 13982, 13959, - 13928, 13888, 13839, 13781, 13715, 13640, 13556, 13464, 13364, 13255, - 13139, 13014, 12882, 12742, 12595, 12440, 12279, 12110, 11935, 11753, - 11565, 11372, 11172, 10967, 10757, 10541, 10321, 10097, 9868, 9635, - 9399, 9160, 8917, 8672, 8424, 8175, 7923, 7670, 7416, 7161, - 6906, 6651, 6396, 6141, 5887, 5635, 5384, 5135, 4888, 4644, - 4402, 4164, 3929, 3699, 3472, 3250, 3033, 2821, 2614, 2413, - 2219, 2030, 1849, 1674, 1506, 1346, 1194, 1050, 914, 786, - 668, 558, 458, 367, 285, 214, 152, 101, 60, 29, - 9, 0, 2, 15, 39, 74, 121, 178, 248, 329, - 421, 525, 640, 767, 906, 1056, 1218, 1391, 1575, 1771, - 1978, 2196, 2425, 2665, 2916, 3177, 3449, 3732, 4024, 4326, - 4639, 4960, 5291, 5632, 5981, 6338, 6704, 7079, 7460, 7850, - 8247, 8650, 9060, 9477, 9899, 10327, 10760, 11198, 11641, 12087, - 12538, 12992, 13449, 13908, 14370, 14834, 15298, 15764, 16231, 16698, - 17164, 17630, 18094, 18557, 19018, 19477, 19933, 20385, 20834, 21279, - 21719, 22154, 22584, 23007, 23425, 23836, 24240, 24636, 25024, 25404, - 25776, 26138, 26491, 26833, 27166, 27488, 27799, 28098, 28386, 28662, - 28925, 29176, 29413, 29637, 29848, 30045, 30227, 30396, 30549, 30687, - 30811, 30918, 31011, 31087, 31147, 31192, 31220, 31231, 31226, 31204, - 31165, 31109, 31036, 30946, 30839, 30714, 30573, 30414, 30237, 30044, - 29833, 29605, 29360, 29098, 28818, 28522, 28209, 27879, 27533, 27170, - 26791, 26396, 25985, 25558, 25116, 24658, 24185, 23698, 23196, 22680, - 22149, 21605, 21048, 20478, 19894, 19299, 18691, 18072, 17441, 16800, - 16148, 15485, 14813, 14132, 13441, 12742, 12035, 11321, 10599, 9870, - 9135, 8395, 7649, 6898, 6142, 5383, 4620, 3855, 3087, 2317, - 1545, 773, 0, -773, -1545, -2317, -3087, -3855, -4620, -5383, - -6142, -6898, -7649, -8395, -9135, -9870, -10599, -11321, -12035, -12742, - -13441, -14132, -14813, -15485, -16148, -16800, -17441, -18072, -18691, -19299, - -19894, -20478, -21048, -21605, -22149, -22680, -23196, -23698, -24185, -24658, - -25116, -25558, -25985, -26396, -26791, -27170, -27533, -27879, -28209, -28522, - -28818, -29098, -29360, -29605, -29833, -30044, -30237, -30414, -30573, -30714, - -30839, -30946, -31036, -31109, -31165, -31204, -31226, -31231, -31220, -31192, - -31147, -31087, -31011, -30918, -30811, -30687, -30549, -30396, -30227, -30045, - -29848, -29637, -29413, -29176, -28925, -28662, -28386, -28098, -27799, -27488, - -27166, -26833, -26491, -26138, -25776, -25404, -25024, -24636, -24240, -23836, - -23425, -23007, -22584, -22154, -21719, -21279, -20834, -20385, -19933, -19477, - -19018, -18557, -18094, -17630, -17164, -16698, -16231, -15764, -15298, -14834, - -14370, -13908, -13449, -12992, -12538, -12087, -11641, -11198, -10760, -10327, - -9899, -9477, -9060, -8650, -8247, -7850, -7460, -7079, -6704, -6338, - -5981, -5632, -5291, -4960, -4639, -4326, -4024, -3732, -3449, -3177, - -2916, -2665, -2425, -2196, -1978, -1771, -1575, -1391, -1218, -1056, - -906, -767, -640, -525, -421, -329, -248, -178, -121, -74, - -39, -15, -2, 0, -9, -29, -60, -101, -152, -214, - -285, -367, -458, -558, -668, -786, -914, -1050, -1194, -1346, - -1506, -1674, -1849, -2030, -2219, -2413, -2614, -2821, -3033, -3250, - -3472, -3699, -3929, -4164, -4402, -4644, -4888, -5135, -5384, -5635, - -5887, -6141, -6396, -6651, -6906, -7161, -7416, -7670, -7923, -8175, - -8424, -8672, -8917, -9160, -9399, -9635, -9868, -10097, -10321, -10541, - -10757, -10967, -11172, -11372, -11565, -11753, -11935, -12110, -12279, -12440, - -12595, -12742, -12882, -13014, -13139, -13255, -13364, -13464, -13556, -13640, - -13715, -13781, -13839, -13888, -13928, -13959, -13982, -13995, -14000, -13995, - -13982, -13959, -13928, -13888, -13839, -13781, -13715, -13640, -13556, -13464, - -13364, -13255, -13139, -13014, -12882, -12742, -12595, -12440, -12279, -12110, - -11935, -11753, -11565, -11372, -11172, -10967, -10757, -10541, -10321, -10097, - -9868, -9635, -9399, -9160, -8917, -8672, -8424, -8175, -7923, -7670, - -7416, -7161, -6906, -6651, -6396, -6141, -5887, -5635, -5384, -5135, - -4888, -4644, -4402, -4164, -3929, -3699, -3472, -3250, -3033, -2821, - -2614, -2413, -2219, -2030, -1849, -1674, -1506, -1346, -1194, -1050, - -914, -786, -668, -558, -458, -367, -285, -214, -152, -101, - -60, -29, -9, 0, -2, -15, -39, -74, -121, -178, - -248, -329, -421, -525, -640, -767, -906, -1056, -1218, -1391, - -1575, -1771, -1978, -2196, -2425, -2665, -2916, -3177, -3449, -3732, - -4024, -4326, -4639, -4960, -5291, -5632, -5981, -6338, -6704, -7079, - -7460, -7850, -8247, -8650, -9060, -9477, -9899, -10327, -10760, -11198, - -11641, -12087, -12538, -12992, -13449, -13908, -14370, -14834, -15298, -15764, - -16231, -16698, -17164, -17630, -18094, -18557, -19018, -19477, -19933, -20385, - -20834, -21279, -21719, -22154, -22584, -23007, -23425, -23836, -24240, -24636, - -25024, -25404, -25776, -26138, -26491, -26833, -27166, -27488, -27799, -28098, - -28386, -28662, -28925, -29176, -29413, -29637, -29848, -30045, -30227, -30396, - -30549, -30687, -30811, -30918, -31011, -31087, -31147, -31192, -31220, -31231, - -31226, -31204, -31165, -31109, -31036, -30946, -30839, -30714, -30573, -30414, - -30237, -30044, -29833, -29605, -29360, -29098, -28818, -28522, -28209, -27879, - -27533, -27170, -26791, -26396, -25985, -25558, -25116, -24658, -24185, -23698, - -23196, -22680, -22149, -21605, -21048, -20478, -19894, -19299, -18691, -18072, - -17441, -16800, -16148, -15485, -14813, -14132, -13441, -12742, -12035, -11321, - -10599, -9870, -9135, -8395, -7649, -6898, -6142, -5383, -4620, -3855, - -3087, -2317, -1545, -773, + 0, 763, 1527, 2289, 3050, 3810, 4567, 5322, 6073, 6821, + 7565, 8305, 9039, 9769, 10493, 11211, 11922, 12626, 13324, 14013, + 14695, 15368, 16032, 16688, 17333, 17969, 18595, 19210, 19814, 20408, + 20989, 21559, 22117, 22663, 23196, 23716, 24223, 24717, 25197, 25664, + 26116, 26555, 26979, 27388, 27783, 28163, 28529, 28879, 29214, 29534, + 29838, 30127, 30401, 30659, 30901, 31128, 31340, 31535, 31716, 31880, + 32029, 32163, 32281, 32384, 32472, 32545, 32602, 32645, 32673, 32686, + 32685, 32670, 32640, 32596, 32539, 32468, 32384, 32287, 32176, 32054, + 31918, 31771, 31612, 31441, 31259, 31066, 30863, 30649, 30424, 30191, + 29947, 29695, 29434, 29165, 28887, 28602, 28309, 28010, 27704, 27392, + 27074, 26750, 26421, 26088, 25750, 25408, 25063, 24715, 24363, 24010, + 23654, 23296, 22938, 22578, 22218, 21857, 21497, 21138, 20779, 20422, + 20067, 19713, 19362, 19013, 18668, 18326, 17988, 17653, 17324, 16998, + 16678, 16363, 16054, 15750, 15453, 15162, 14877, 14600, 14329, 14066, + 13811, 13563, 13324, 13092, 12869, 12654, 12449, 12252, 12064, 11885, + 11715, 11555, 11404, 11263, 11132, 11010, 10898, 10796, 10704, 10622, + 10549, 10487, 10435, 10392, 10359, 10337, 10324, 10321, 10327, 10344, + 10369, 10405, 10449, 10503, 10566, 10638, 10719, 10808, 10906, 11013, + 11127, 11250, 11380, 11518, 11664, 11816, 11976, 12142, 12315, 12495, + 12680, 12871, 13067, 13269, 13476, 13688, 13904, 14124, 14348, 14576, + 14807, 15041, 15278, 15517, 15759, 16002, 16247, 16493, 16740, 16988, + 17236, 17484, 17732, 17979, 18225, 18471, 18714, 18957, 19197, 19435, + 19670, 19902, 20132, 20358, 20580, 20798, 21013, 21222, 21427, 21628, + 21823, 22012, 22196, 22375, 22547, 22713, 22873, 23026, 23172, 23311, + 23444, 23569, 23687, 23797, 23899, 23994, 24081, 24160, 24231, 24293, + 24348, 24394, 24432, 24461, 24483, 24495, 24500, 24495, 24483, 24461, + 24432, 24394, 24348, 24293, 24231, 24160, 24081, 23994, 23899, 23797, + 23687, 23569, 23444, 23311, 23172, 23026, 22873, 22713, 22547, 22375, + 22196, 22012, 21823, 21628, 21427, 21222, 21013, 20798, 20580, 20358, + 20132, 19902, 19670, 19435, 19197, 18957, 18714, 18471, 18225, 17979, + 17732, 17484, 17236, 16988, 16740, 16493, 16247, 16002, 15759, 15517, + 15278, 15041, 14807, 14576, 14348, 14124, 13904, 13688, 13476, 13269, + 13067, 12871, 12680, 12495, 12315, 12142, 11976, 11816, 11664, 11518, + 11380, 11250, 11127, 11013, 10906, 10808, 10719, 10638, 10566, 10503, + 10449, 10405, 10369, 10344, 10327, 10321, 10324, 10337, 10359, 10392, + 10435, 10487, 10549, 10622, 10704, 10796, 10898, 11010, 11132, 11263, + 11404, 11555, 11715, 11885, 12064, 12252, 12449, 12654, 12869, 13092, + 13324, 13563, 13811, 14066, 14329, 14600, 14877, 15162, 15453, 15750, + 16054, 16363, 16678, 16998, 17324, 17653, 17988, 18326, 18668, 19013, + 19362, 19713, 20067, 20422, 20779, 21138, 21497, 21857, 22218, 22578, + 22938, 23296, 23654, 24010, 24363, 24715, 25063, 25408, 25750, 26088, + 26421, 26750, 27074, 27392, 27704, 28010, 28309, 28602, 28887, 29165, + 29434, 29695, 29947, 30191, 30424, 30649, 30863, 31066, 31259, 31441, + 31612, 31771, 31918, 32054, 32176, 32287, 32384, 32468, 32539, 32596, + 32640, 32670, 32685, 32686, 32673, 32645, 32602, 32545, 32472, 32384, + 32281, 32163, 32029, 31880, 31716, 31535, 31340, 31128, 30901, 30659, + 30401, 30127, 29838, 29534, 29214, 28879, 28529, 28163, 27783, 27388, + 26979, 26555, 26116, 25664, 25197, 24717, 24223, 23716, 23196, 22663, + 22117, 21559, 20989, 20408, 19814, 19210, 18595, 17969, 17333, 16688, + 16032, 15368, 14695, 14013, 13324, 12626, 11922, 11211, 10493, 9769, + 9039, 8305, 7565, 6821, 6073, 5322, 4567, 3810, 3050, 2289, + 1527, 763, 0, -763, -1527, -2289, -3050, -3810, -4567, -5322, + -6073, -6821, -7565, -8305, -9039, -9769, -10493, -11211, -11922, -12626, + -13324, -14013, -14695, -15368, -16032, -16688, -17333, -17969, -18595, -19210, + -19814, -20408, -20989, -21559, -22117, -22663, -23196, -23716, -24223, -24717, + -25197, -25664, -26116, -26555, -26979, -27388, -27783, -28163, -28529, -28879, + -29214, -29534, -29838, -30127, -30401, -30659, -30901, -31128, -31340, -31535, + -31716, -31880, -32029, -32163, -32281, -32384, -32472, -32545, -32602, -32645, + -32673, -32686, -32685, -32670, -32640, -32596, -32539, -32468, -32384, -32287, + -32176, -32054, -31918, -31771, -31612, -31441, -31259, -31066, -30863, -30649, + -30424, -30191, -29947, -29695, -29434, -29165, -28887, -28602, -28309, -28010, + -27704, -27392, -27074, -26750, -26421, -26088, -25750, -25408, -25063, -24715, + -24363, -24010, -23654, -23296, -22938, -22578, -22218, -21857, -21497, -21138, + -20779, -20422, -20067, -19713, -19362, -19013, -18668, -18326, -17988, -17653, + -17324, -16998, -16678, -16363, -16054, -15750, -15453, -15162, -14877, -14600, + -14329, -14066, -13811, -13563, -13324, -13092, -12869, -12654, -12449, -12252, + -12064, -11885, -11715, -11555, -11404, -11263, -11132, -11010, -10898, -10796, + -10704, -10622, -10549, -10487, -10435, -10392, -10359, -10337, -10324, -10321, + -10327, -10344, -10369, -10405, -10449, -10503, -10566, -10638, -10719, -10808, + -10906, -11013, -11127, -11250, -11380, -11518, -11664, -11816, -11976, -12142, + -12315, -12495, -12680, -12871, -13067, -13269, -13476, -13688, -13904, -14124, + -14348, -14576, -14807, -15041, -15278, -15517, -15759, -16002, -16247, -16493, + -16740, -16988, -17236, -17484, -17732, -17979, -18225, -18471, -18714, -18957, + -19197, -19435, -19670, -19902, -20132, -20358, -20580, -20798, -21013, -21222, + -21427, -21628, -21823, -22012, -22196, -22375, -22547, -22713, -22873, -23026, + -23172, -23311, -23444, -23569, -23687, -23797, -23899, -23994, -24081, -24160, + -24231, -24293, -24348, -24394, -24432, -24461, -24483, -24495, -24500, -24495, + -24483, -24461, -24432, -24394, -24348, -24293, -24231, -24160, -24081, -23994, + -23899, -23797, -23687, -23569, -23444, -23311, -23172, -23026, -22873, -22713, + -22547, -22375, -22196, -22012, -21823, -21628, -21427, -21222, -21013, -20798, + -20580, -20358, -20132, -19902, -19670, -19435, -19197, -18957, -18714, -18471, + -18225, -17979, -17732, -17484, -17236, -16988, -16740, -16493, -16247, -16002, + -15759, -15517, -15278, -15041, -14807, -14576, -14348, -14124, -13904, -13688, + -13476, -13269, -13067, -12871, -12680, -12495, -12315, -12142, -11976, -11816, + -11664, -11518, -11380, -11250, -11127, -11013, -10906, -10808, -10719, -10638, + -10566, -10503, -10449, -10405, -10369, -10344, -10327, -10321, -10324, -10337, + -10359, -10392, -10435, -10487, -10549, -10622, -10704, -10796, -10898, -11010, + -11132, -11263, -11404, -11555, -11715, -11885, -12064, -12252, -12449, -12654, + -12869, -13092, -13324, -13563, -13811, -14066, -14329, -14600, -14877, -15162, + -15453, -15750, -16054, -16363, -16678, -16998, -17324, -17653, -17988, -18326, + -18668, -19013, -19362, -19713, -20067, -20422, -20779, -21138, -21497, -21857, + -22218, -22578, -22938, -23296, -23654, -24010, -24363, -24715, -25063, -25408, + -25750, -26088, -26421, -26750, -27074, -27392, -27704, -28010, -28309, -28602, + -28887, -29165, -29434, -29695, -29947, -30191, -30424, -30649, -30863, -31066, + -31259, -31441, -31612, -31771, -31918, -32054, -32176, -32287, -32384, -32468, + -32539, -32596, -32640, -32670, -32685, -32686, -32673, -32645, -32602, -32545, + -32472, -32384, -32281, -32163, -32029, -31880, -31716, -31535, -31340, -31128, + -30901, -30659, -30401, -30127, -29838, -29534, -29214, -28879, -28529, -28163, + -27783, -27388, -26979, -26555, -26116, -25664, -25197, -24717, -24223, -23716, + -23196, -22663, -22117, -21559, -20989, -20408, -19814, -19210, -18595, -17969, + -17333, -16688, -16032, -15368, -14695, -14013, -13324, -12626, -11922, -11211, + -10493, -9769, -9039, -8305, -7565, -6821, -6073, -5322, -4567, -3810, + -3050, -2289, -1527, -763, + }; #if defined(SDCARD) diff --git a/radio/util/sinus.py b/radio/util/sinus.py index cce2efce3..e852b7427 100644 --- a/radio/util/sinus.py +++ b/radio/util/sinus.py @@ -3,14 +3,27 @@ import math samples = 1024 -amplitudes = (28000, 0, 28000, 0, 28000) +amplitudes = (49000, 0, 25000, 0, 25000) + +max = 0 +min = 0 for i in range(samples): - sample = 0.0 - for harmonic, amplitude in enumerate(amplitudes): - sample += math.sin(math.pi*2*i*(harmonic+1)/samples) * amplitude / 2 - if sample > 32767 or sample < -32768: - print "erreur" - print "%d," % int(sample), - if i % 10 == 9: - print + sample = 0.0 + for harmonic, amplitude in enumerate(amplitudes): + sample += math.sin(math.pi*2*i*(harmonic+1)/samples) * amplitude / 2 + sample = int(sample) + if sample > max: + max = sample + elif sample < min: + min = sample + print "%d," % sample, + if i % 10 == 9: + print + +print +print 'Range is:', min, max + +if max > 32767 or min < -32768: + print "Invalid range!" + From 23b3ea18564315be8a57c34f3135e2762f6fdae6 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Fri, 21 Feb 2014 11:58:19 +0100 Subject: [PATCH 34/89] Background Music should now stop correctly when switch is OFF --- radio/src/audio_arm.cpp | 2 +- radio/src/opentx.cpp | 7 +------ 2 files changed, 2 insertions(+), 7 deletions(-) diff --git a/radio/src/audio_arm.cpp b/radio/src/audio_arm.cpp index 1340ccd7d..7a2bb3468 100644 --- a/radio/src/audio_arm.cpp +++ b/radio/src/audio_arm.cpp @@ -622,7 +622,7 @@ void AudioQueue::wakeup() } // mix the background context - if (!isFunctionActive(FUNCTION_BACKGND_MUSIC_PAUSE)) { + if (isFunctionActive(FUNCTION_BACKGND_MUSIC) && !isFunctionActive(FUNCTION_BACKGND_MUSIC_PAUSE)) { result = backgroundContext.mixBuffer(buffer, g_eeGeneral.backgroundVolume, fade); if (result > 0) { size = max(size, result); diff --git a/radio/src/opentx.cpp b/radio/src/opentx.cpp index 3fbd2d5e6..2be47461e 100644 --- a/radio/src/opentx.cpp +++ b/radio/src/opentx.cpp @@ -3259,7 +3259,7 @@ void evalFunctions() if (active || IS_PLAY_BOTH_FUNC(CFN_FUNC(sd))) { - switch(CFN_FUNC(sd)) { + switch (CFN_FUNC(sd)) { case FUNC_SAFETY_CHANNEL: safetyCh[CFN_CH_INDEX(sd)] = CFN_PARAM(sd); @@ -3479,11 +3479,6 @@ void evalFunctions() lastFunctionTime[i] = 0; #if defined(CPUARM) fnSwitchDuration[i] = 0; -#endif -#if defined(CPUARM) && defined(SDCARD) - if (CFN_FUNC(sd) == FUNC_BACKGND_MUSIC && isFunctionActive(FUNCTION_BACKGND_MUSIC)) { - STOP_PLAY(i+1); - } #endif } } From bb774648ff594238bb85cb9ddbde9375f5c147a7 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Fri, 21 Feb 2014 12:16:05 +0100 Subject: [PATCH 35/89] P25 and P26 automatic prompts were not played --- radio/src/audio_arm.cpp | 4 ++-- radio/src/opentx.cpp | 3 ++- 2 files changed, 4 insertions(+), 3 deletions(-) diff --git a/radio/src/audio_arm.cpp b/radio/src/audio_arm.cpp index 7f1d92d52..6a6d84010 100644 --- a/radio/src/audio_arm.cpp +++ b/radio/src/audio_arm.cpp @@ -118,12 +118,12 @@ const char * audioFilenames[] = { uint64_t sdAvailableSystemAudioFiles = 0; uint32_t sdAvailablePhaseAudioFiles = 0; -uint32_t sdAvailableSwitchAudioFiles = 0; +uint64_t sdAvailableSwitchAudioFiles = 0; uint64_t sdAvailableLogicalSwitchAudioFiles = 0; #define MASK_SYSTEM_AUDIO_FILE(index) ((uint64_t)1 << index) #define MASK_PHASE_AUDIO_FILE(index, event) ((uint32_t)1 << (2*index+event)) -#define MASK_SWITCH_AUDIO_FILE(index) ((uint32_t)1 << index) +#define MASK_SWITCH_AUDIO_FILE(index) ((uint64_t)1 << index) #define MASK_LOGICAL_SWITCH_AUDIO_FILE(index, event) ((uint64_t)1 << (2*index+event)) bool isFileAvailable(const char * filename) diff --git a/radio/src/opentx.cpp b/radio/src/opentx.cpp index 7955f57b4..7b5a609de 100644 --- a/radio/src/opentx.cpp +++ b/radio/src/opentx.cpp @@ -1309,7 +1309,6 @@ getvalue_t getValue(uint8_t i) volatile GETSWITCH_RECURSIVE_TYPE s_last_switch_used = 0; volatile GETSWITCH_RECURSIVE_TYPE s_last_switch_value = 0; -/* recursive function. stack as of today (16/03/2012) grows by 8bytes at each call, which is ok! */ #if defined(CPUARM) uint32_t cswDelays[NUM_CSW]; @@ -1425,6 +1424,8 @@ void getSwitchesPosition(bool play) int16_t csLastValue[NUM_CSW]; #define CS_LAST_VALUE_INIT -32768 + +/* recursive function. stack as of today (16/03/2012) grows by 8bytes at each call, which is ok! */ bool getSwitch(int8_t swtch) { bool result; From 5dbf2063f81665acf39148528627765348b9e702 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Fri, 21 Feb 2014 14:47:38 +0100 Subject: [PATCH 36/89] 6-pos and 3-pos switches shouldn't be played at startup now --- radio/src/opentx.cpp | 37 +++++++++++++++++++------------------ 1 file changed, 19 insertions(+), 18 deletions(-) diff --git a/radio/src/opentx.cpp b/radio/src/opentx.cpp index 0f84855d8..c35f84ccb 100644 --- a/radio/src/opentx.cpp +++ b/radio/src/opentx.cpp @@ -1327,7 +1327,7 @@ uint32_t switchesPos = 0; tmr10ms_t potsLastposStart[NUM_XPOTS]; uint8_t potsPos[NUM_XPOTS]; -uint32_t check2PosSwitchPosition(EnumKeys sw, bool play) +uint32_t check2PosSwitchPosition(EnumKeys sw, bool startup) { uint32_t result; uint32_t index; @@ -1339,7 +1339,7 @@ uint32_t check2PosSwitchPosition(EnumKeys sw, bool play) result = (1 << index); - if (play && !(switchesPos & result)) { + if (!startup && !(switchesPos & result)) { PLAY_SWITCH_MOVED(index); } @@ -1347,7 +1347,7 @@ uint32_t check2PosSwitchPosition(EnumKeys sw, bool play) } #define DELAY_SWITCH_3POS 10/*100ms*/ -uint32_t check3PosSwitchPosition(uint8_t idx, EnumKeys sw, bool play) +uint32_t check3PosSwitchPosition(uint8_t idx, EnumKeys sw, bool startup) { uint32_t result; uint32_t index; @@ -1362,7 +1362,7 @@ uint32_t check3PosSwitchPosition(uint8_t idx, EnumKeys sw, bool play) result = (1 << index); switchesMidposStart[idx] = 0; } - else if ((switchesPos & (1 << (sw - SW_SA0 + 1))) || (switchesMidposStart[idx] && (tmr10ms_t)(get_tmr10ms() - switchesMidposStart[idx]) > DELAY_SWITCH_3POS)) { + else if (startup || (switchesPos & (1 << (sw - SW_SA0 + 1))) || (switchesMidposStart[idx] && (tmr10ms_t)(get_tmr10ms() - switchesMidposStart[idx]) > DELAY_SWITCH_3POS)) { index = sw - SW_SA0 + 1; result = (1 << index); switchesMidposStart[idx] = 0; @@ -1375,17 +1375,17 @@ uint32_t check3PosSwitchPosition(uint8_t idx, EnumKeys sw, bool play) result = (switchesPos & (0x7 << (sw - SW_SA0))); } - if (play && !(switchesPos & result)) { + if (!startup && !(switchesPos & result)) { PLAY_SWITCH_MOVED(index); } return result; } -#define CHECK_2POS(sw) newPos |= check2PosSwitchPosition(sw ## 0, play) -#define CHECK_3POS(idx, sw) newPos |= check3PosSwitchPosition(idx, sw ## 0, play) +#define CHECK_2POS(sw) newPos |= check2PosSwitchPosition(sw ## 0, startup) +#define CHECK_3POS(idx, sw) newPos |= check3PosSwitchPosition(idx, sw ## 0, startup) -void getSwitchesPosition(bool play) +void getSwitchesPosition(bool startup) { uint32_t newPos = 0; CHECK_3POS(0, SW_SA); @@ -1409,10 +1409,10 @@ void getSwitchesPosition(bool play) potsLastposStart[i] = get_tmr10ms(); potsPos[i] = (pos << 4) | previousStoredPos; } - else if ((tmr10ms_t)(get_tmr10ms() - potsLastposStart[i]) > DELAY_SWITCH_3POS) { + else if (startup || (tmr10ms_t)(get_tmr10ms() - potsLastposStart[i]) > DELAY_SWITCH_3POS) { potsLastposStart[i] = 0; potsPos[i] = (pos << 4) | pos; - if (play && previousStoredPos != pos) { + if (!startup && previousStoredPos != pos) { PLAY_SWITCH_MOVED(SWSRC_LAST_SWITCH+i*POTS_POS_COUNT+pos); } } @@ -2460,14 +2460,15 @@ void checkSwitches() } } uint8_t potMode = g_model.nPotsToWarn >> 6; - if(potMode) { + if (potMode) { perOut(e_perout_mode_normal, 0); bad_pots = 0; - for (uint8_t i=0; i> 3)) > 2)) { - warn = true; - bad_pots |= (1<> 3)) > 2)) { + warn = true; + bad_pots |= (1<> (i*2)]; @@ -4018,7 +4019,7 @@ void doMixerCalculations() getADC(); - getSwitchesPosition(lastTMR != 0); + getSwitchesPosition(lastTMR == 0); #if defined(CPUARM) lastTMR = tmr10ms; From 095bb38c0375476d7397445a85df1ec0cbca075e Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Fri, 21 Feb 2014 15:18:05 +0100 Subject: [PATCH 37/89] Now logical switches automatic prompts --- radio/src/audio_arm.cpp | 4 +++- radio/src/audio_arm.h | 13 ++++++++++--- radio/src/opentx.cpp | 23 +++++++++++++++-------- 3 files changed, 28 insertions(+), 12 deletions(-) diff --git a/radio/src/audio_arm.cpp b/radio/src/audio_arm.cpp index 6a6d84010..686c000f3 100644 --- a/radio/src/audio_arm.cpp +++ b/radio/src/audio_arm.cpp @@ -318,10 +318,12 @@ bool isAudioFileReferenced(uint32_t i, char * filename) return false; } +tmr10ms_t timeAutomaticPromptsSilence = 0; + void playModelEvent(uint8_t category, uint8_t index, uint8_t event) { char filename[AUDIO_FILENAME_MAXLEN+1]; - if (isAudioFileReferenced((category << 24) + (index << 16) + event, filename)) { + if ((get_tmr10ms()-timeAutomaticPromptsSilence > 10) && isAudioFileReferenced((category << 24) + (index << 16) + event, filename)) { audioQueue.playFile(filename); } } diff --git a/radio/src/audio_arm.h b/radio/src/audio_arm.h index 8c67fad5e..3f5ee974c 100644 --- a/radio/src/audio_arm.h +++ b/radio/src/audio_arm.h @@ -305,14 +305,21 @@ void pushPrompt(uint16_t prompt, uint8_t id=0); #define AUDIO_RESET() audioQueue.reset() #if defined(SDCARD) + extern tmr10ms_t timeAutomaticPromptsSilence; void playModelEvent(uint8_t category, uint8_t index, uint8_t event=0); - #define PLAY_PHASE_OFF(phase) playModelEvent(PHASE_AUDIO_CATEGORY, phase, AUDIO_EVENT_OFF) - #define PLAY_PHASE_ON(phase) playModelEvent(PHASE_AUDIO_CATEGORY, phase, AUDIO_EVENT_ON) - #define PLAY_SWITCH_MOVED(sw) playModelEvent(SWITCH_AUDIO_CATEGORY, sw) + #define PLAY_PHASE_OFF(phase) playModelEvent(PHASE_AUDIO_CATEGORY, phase, AUDIO_EVENT_OFF) + #define PLAY_PHASE_ON(phase) playModelEvent(PHASE_AUDIO_CATEGORY, phase, AUDIO_EVENT_ON) + #define PLAY_SWITCH_MOVED(sw) playModelEvent(SWITCH_AUDIO_CATEGORY, sw) + #define PLAY_LOGICAL_SWITCH_OFF(sw) playModelEvent(LOGICAL_SWITCH_AUDIO_CATEGORY, sw, AUDIO_EVENT_OFF) + #define PLAY_LOGICAL_SWITCH_ON(sw) playModelEvent(LOGICAL_SWITCH_AUDIO_CATEGORY, sw, AUDIO_EVENT_ON) + #define SKIP_AUTOMATIC_PROMPTS() timeAutomaticPromptsSilence = get_tmr10ms() #else #define PLAY_PHASE_OFF(phase) #define PLAY_PHASE_ON(phase) #define PLAY_SWITCH_MOVED(sw) + #define PLAY_LOGICAL_SWITCH_OFF(sw) + #define PLAY_LOGICAL_SWITCH_ON(sw) + #define SKIP_AUTOMATIC_PROMPTS() #endif void referenceSystemAudioFiles(); diff --git a/radio/src/opentx.cpp b/radio/src/opentx.cpp index c35f84ccb..2cb2b37a8 100644 --- a/radio/src/opentx.cpp +++ b/radio/src/opentx.cpp @@ -1327,7 +1327,7 @@ uint32_t switchesPos = 0; tmr10ms_t potsLastposStart[NUM_XPOTS]; uint8_t potsPos[NUM_XPOTS]; -uint32_t check2PosSwitchPosition(EnumKeys sw, bool startup) +uint32_t check2PosSwitchPosition(EnumKeys sw) { uint32_t result; uint32_t index; @@ -1339,7 +1339,7 @@ uint32_t check2PosSwitchPosition(EnumKeys sw, bool startup) result = (1 << index); - if (!startup && !(switchesPos & result)) { + if (!(switchesPos & result)) { PLAY_SWITCH_MOVED(index); } @@ -1375,14 +1375,14 @@ uint32_t check3PosSwitchPosition(uint8_t idx, EnumKeys sw, bool startup) result = (switchesPos & (0x7 << (sw - SW_SA0))); } - if (!startup && !(switchesPos & result)) { + if (!(switchesPos & result)) { PLAY_SWITCH_MOVED(index); } return result; } -#define CHECK_2POS(sw) newPos |= check2PosSwitchPosition(sw ## 0, startup) +#define CHECK_2POS(sw) newPos |= check2PosSwitchPosition(sw ## 0) #define CHECK_3POS(idx, sw) newPos |= check3PosSwitchPosition(idx, sw ## 0, startup) void getSwitchesPosition(bool startup) @@ -1412,7 +1412,7 @@ void getSwitchesPosition(bool startup) else if (startup || (tmr10ms_t)(get_tmr10ms() - potsLastposStart[i]) > DELAY_SWITCH_3POS) { potsLastposStart[i] = 0; potsPos[i] = (pos << 4) | pos; - if (!startup && previousStoredPos != pos) { + if (previousStoredPos != pos) { PLAY_SWITCH_MOVED(SWSRC_LAST_SWITCH+i*POTS_POS_COUNT+pos); } } @@ -1650,10 +1650,14 @@ bool getSwitch(int8_t swtch) } #endif - if (result) + if (result) { + PLAY_LOGICAL_SWITCH_ON(cs_idx); s_last_switch_value |= mask; - else + } + else { + PLAY_LOGICAL_SWITCH_OFF(cs_idx); s_last_switch_value &= ~mask; + } } } @@ -2998,11 +3002,14 @@ void resetAll() #if defined(FRSKY) resetTelemetry(); #endif - for (uint8_t i=0; i Date: Fri, 21 Feb 2014 15:54:53 +0100 Subject: [PATCH 38/89] Compilation was broken --- radio/src/audio_avr.h | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/radio/src/audio_avr.h b/radio/src/audio_avr.h index 6302c13f4..691305655 100644 --- a/radio/src/audio_avr.h +++ b/radio/src/audio_avr.h @@ -157,5 +157,9 @@ void audioDefevent(uint8_t e); #define PLAY_PHASE_OFF(phase) #define PLAY_PHASE_ON(phase) +#define PLAY_SWITCH_MOVED(sw) +#define PLAY_LOGICAL_SWITCH_OFF(sw) +#define PLAY_LOGICAL_SWITCH_ON(sw) +#define SKIP_AUTOMATIC_PROMPTS() #endif From 5f560e8d1b2815267f118be59c9269ed42357d66 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Fri, 21 Feb 2014 15:57:00 +0100 Subject: [PATCH 39/89] No more parsing of all system sounds. Automatic prompts silent after alerts --- radio/src/audio_arm.cpp | 66 +++++++++++++++++++++++++++++++---------- radio/src/buzzer.h | 4 +++ radio/src/opentx.cpp | 2 ++ radio/src/sdcard.h | 2 +- 4 files changed, 57 insertions(+), 17 deletions(-) diff --git a/radio/src/audio_arm.cpp b/radio/src/audio_arm.cpp index 686c000f3..671547add 100644 --- a/radio/src/audio_arm.cpp +++ b/radio/src/audio_arm.cpp @@ -135,26 +135,63 @@ bool isFileAvailable(const char * filename) return f_stat(filename, &info) == FR_OK; } +char * getAudioPath(char * path) +{ + strcpy(path, SOUNDS_PATH "/"); + strncpy(path+SOUNDS_PATH_LNG_OFS, currentLanguagePack->id, 2); + return path + sizeof(SOUNDS_PATH); +} + +char * getSystemAudioPath(char * path) +{ + char * str = getAudioPath(path); + strcpy(path, SYSTEM_SUBDIR "/"); + return str + sizeof(SYSTEM_SUBDIR); +} + void getSystemAudioFile(char * filename, int index) { - strcpy(filename, SYSTEM_SOUNDS_PATH "/"); - strncpy(filename+SOUNDS_PATH_LNG_OFS, currentLanguagePack->id, 2); - strcpy(filename+sizeof(SYSTEM_SOUNDS_PATH), audioFilenames[index]); - strcat(filename+sizeof(SYSTEM_SOUNDS_PATH), SOUNDS_EXT); + char * str = getAudioPath(filename); + strcpy(str, audioFilenames[index]); + strcat(str, SOUNDS_EXT); } void referenceSystemAudioFiles() { - char filename[AUDIO_FILENAME_MAXLEN+1]; + char path[AUDIO_FILENAME_MAXLEN+1]; + FILINFO fno; + DIR dir; + char *fn; /* This function is assuming non-Unicode cfg. */ + TCHAR lfn[_MAX_LFN + 1]; + fno.lfname = lfn; + fno.lfsize = sizeof(lfn); + uint64_t availableAudioFiles = 0; assert(sizeof(audioFilenames)==AU_FRSKY_FIRST*sizeof(char *)); assert(sizeof(sdAvailableSystemAudioFiles)*8 >= AU_FRSKY_FIRST); - for (int i=0; iid, 2); - + char filename[AUDIO_FILENAME_MAXLEN+1]; + char * str = getSystemAudioPath(filename); + strcpy(str, "0000" SOUNDS_EXT); for (int8_t i=3; i>=0; i--) { - filename[sizeof(SYSTEM_SOUNDS_PATH)+i] = '0' + (prompt%10); + str[i] = '0' + (prompt%10); prompt /= 10; } - audioQueue.playFile(filename, 0, id); - #endif } diff --git a/radio/src/buzzer.h b/radio/src/buzzer.h index cbb4d5717..6d901bbbb 100644 --- a/radio/src/buzzer.h +++ b/radio/src/buzzer.h @@ -102,6 +102,10 @@ void beep(uint8_t val); #define PLAY_PHASE_OFF(phase) #define PLAY_PHASE_ON(phase) + #define PLAY_SWITCH_MOVED(sw) + #define PLAY_LOGICAL_SWITCH_OFF(sw) + #define PLAY_LOGICAL_SWITCH_ON(sw) + #define SKIP_AUTOMATIC_PROMPTS() #endif #if !defined(CPUARM) diff --git a/radio/src/opentx.cpp b/radio/src/opentx.cpp index 2cb2b37a8..44cdcf50a 100644 --- a/radio/src/opentx.cpp +++ b/radio/src/opentx.cpp @@ -2347,6 +2347,8 @@ void checkAll() #endif clearKeyEvents(); + + SKIP_AUTOMATIC_PROMPTS(); } #if defined(MODULE_ALWAYS_SEND_PULSES) diff --git a/radio/src/sdcard.h b/radio/src/sdcard.h index 07e528a68..ccbad5fa6 100644 --- a/radio/src/sdcard.h +++ b/radio/src/sdcard.h @@ -44,7 +44,7 @@ #define LOGS_PATH ROOT_PATH "LOGS" // no trailing slash = important #define SOUNDS_PATH ROOT_PATH "SOUNDS/en" // no trailing slash = important #define SOUNDS_PATH_LNG_OFS (sizeof(SOUNDS_PATH)-3) -#define SYSTEM_SOUNDS_PATH SOUNDS_PATH "/SYSTEM" // no trailing slash = important +#define SYSTEM_SUBDIR "SYSTEM" // no trailing slash = important #define BITMAPS_PATH ROOT_PATH "BMP" #define SCRIPTS_PATH ROOT_PATH "SCRIPTS" From 03451730396f901983e0c2db891f5f5cdac5c88a Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Fri, 21 Feb 2014 15:57:00 +0100 Subject: [PATCH 40/89] No more parsing of all system sounds. Automatic prompts silent after alerts --- radio/src/audio_arm.cpp | 66 +++++++++++++++++++++++++++++++---------- radio/src/buzzer.h | 4 +++ radio/src/opentx.cpp | 2 ++ radio/src/sdcard.h | 2 +- 4 files changed, 57 insertions(+), 17 deletions(-) diff --git a/radio/src/audio_arm.cpp b/radio/src/audio_arm.cpp index 686c000f3..b1229f1cc 100644 --- a/radio/src/audio_arm.cpp +++ b/radio/src/audio_arm.cpp @@ -135,26 +135,63 @@ bool isFileAvailable(const char * filename) return f_stat(filename, &info) == FR_OK; } +char * getAudioPath(char * path) +{ + strcpy(path, SOUNDS_PATH "/"); + strncpy(path+SOUNDS_PATH_LNG_OFS, currentLanguagePack->id, 2); + return path + sizeof(SOUNDS_PATH); +} + +char * getSystemAudioPath(char * path) +{ + char * str = getAudioPath(path); + strcpy(str, SYSTEM_SUBDIR "/"); + return str + sizeof(SYSTEM_SUBDIR); +} + void getSystemAudioFile(char * filename, int index) { - strcpy(filename, SYSTEM_SOUNDS_PATH "/"); - strncpy(filename+SOUNDS_PATH_LNG_OFS, currentLanguagePack->id, 2); - strcpy(filename+sizeof(SYSTEM_SOUNDS_PATH), audioFilenames[index]); - strcat(filename+sizeof(SYSTEM_SOUNDS_PATH), SOUNDS_EXT); + char * str = getAudioPath(filename); + strcpy(str, audioFilenames[index]); + strcat(str, SOUNDS_EXT); } void referenceSystemAudioFiles() { - char filename[AUDIO_FILENAME_MAXLEN+1]; + char path[AUDIO_FILENAME_MAXLEN+1]; + FILINFO fno; + DIR dir; + char *fn; /* This function is assuming non-Unicode cfg. */ + TCHAR lfn[_MAX_LFN + 1]; + fno.lfname = lfn; + fno.lfsize = sizeof(lfn); + uint64_t availableAudioFiles = 0; assert(sizeof(audioFilenames)==AU_FRSKY_FIRST*sizeof(char *)); assert(sizeof(sdAvailableSystemAudioFiles)*8 >= AU_FRSKY_FIRST); - for (int i=0; iid, 2); - + char filename[AUDIO_FILENAME_MAXLEN+1]; + char * str = getSystemAudioPath(filename); + strcpy(str, "0000" SOUNDS_EXT); for (int8_t i=3; i>=0; i--) { - filename[sizeof(SYSTEM_SOUNDS_PATH)+i] = '0' + (prompt%10); + str[i] = '0' + (prompt%10); prompt /= 10; } - audioQueue.playFile(filename, 0, id); - #endif } diff --git a/radio/src/buzzer.h b/radio/src/buzzer.h index cbb4d5717..6d901bbbb 100644 --- a/radio/src/buzzer.h +++ b/radio/src/buzzer.h @@ -102,6 +102,10 @@ void beep(uint8_t val); #define PLAY_PHASE_OFF(phase) #define PLAY_PHASE_ON(phase) + #define PLAY_SWITCH_MOVED(sw) + #define PLAY_LOGICAL_SWITCH_OFF(sw) + #define PLAY_LOGICAL_SWITCH_ON(sw) + #define SKIP_AUTOMATIC_PROMPTS() #endif #if !defined(CPUARM) diff --git a/radio/src/opentx.cpp b/radio/src/opentx.cpp index 2cb2b37a8..44cdcf50a 100644 --- a/radio/src/opentx.cpp +++ b/radio/src/opentx.cpp @@ -2347,6 +2347,8 @@ void checkAll() #endif clearKeyEvents(); + + SKIP_AUTOMATIC_PROMPTS(); } #if defined(MODULE_ALWAYS_SEND_PULSES) diff --git a/radio/src/sdcard.h b/radio/src/sdcard.h index 07e528a68..ccbad5fa6 100644 --- a/radio/src/sdcard.h +++ b/radio/src/sdcard.h @@ -44,7 +44,7 @@ #define LOGS_PATH ROOT_PATH "LOGS" // no trailing slash = important #define SOUNDS_PATH ROOT_PATH "SOUNDS/en" // no trailing slash = important #define SOUNDS_PATH_LNG_OFS (sizeof(SOUNDS_PATH)-3) -#define SYSTEM_SOUNDS_PATH SOUNDS_PATH "/SYSTEM" // no trailing slash = important +#define SYSTEM_SUBDIR "SYSTEM" // no trailing slash = important #define BITMAPS_PATH ROOT_PATH "BMP" #define SCRIPTS_PATH ROOT_PATH "SCRIPTS" From d02912577b22462c491ddd78d8f328d84e3577c0 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Fri, 21 Feb 2014 16:51:51 +0100 Subject: [PATCH 41/89] Merge problem :( --- radio/src/audio_arm.cpp | 4 ---- 1 file changed, 4 deletions(-) diff --git a/radio/src/audio_arm.cpp b/radio/src/audio_arm.cpp index 678d173e0..b1229f1cc 100644 --- a/radio/src/audio_arm.cpp +++ b/radio/src/audio_arm.cpp @@ -145,11 +145,7 @@ char * getAudioPath(char * path) char * getSystemAudioPath(char * path) { char * str = getAudioPath(path); -<<<<<<< HEAD strcpy(str, SYSTEM_SUBDIR "/"); -======= - strcpy(path, SYSTEM_SUBDIR "/"); ->>>>>>> 5f560e8d1b2815267f118be59c9269ed42357d66 return str + sizeof(SYSTEM_SUBDIR); } From a7bba2a578b1f6a42b44169d3988b7feeeaa12d9 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Fri, 21 Feb 2014 16:55:43 +0100 Subject: [PATCH 42/89] Logical switches automatic prompts bugfix --- radio/src/opentx.cpp | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/radio/src/opentx.cpp b/radio/src/opentx.cpp index 44cdcf50a..6ce62a3f6 100644 --- a/radio/src/opentx.cpp +++ b/radio/src/opentx.cpp @@ -1651,11 +1651,11 @@ bool getSwitch(int8_t swtch) #endif if (result) { - PLAY_LOGICAL_SWITCH_ON(cs_idx); + if (!(s_last_switch_value&mask)) PLAY_LOGICAL_SWITCH_ON(cs_idx); s_last_switch_value |= mask; } else { - PLAY_LOGICAL_SWITCH_OFF(cs_idx); + if (s_last_switch_value&mask) PLAY_LOGICAL_SWITCH_OFF(cs_idx); s_last_switch_value &= ~mask; } } @@ -3405,7 +3405,7 @@ void evalFunctions() if (active || IS_PLAY_BOTH_FUNC(CFN_FUNC(sd))) { - switch(CFN_FUNC(sd)) { + switch (CFN_FUNC(sd)) { case FUNC_SAFETY_CHANNEL: safetyCh[CFN_CH_INDEX(sd)] = CFN_PARAM(sd); From 9b5b22658a392759e3a9863225b6b22e502ba262 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Fri, 21 Feb 2014 17:09:03 +0100 Subject: [PATCH 43/89] Cosmetics --- radio/src/opentx.cpp | 43 +++++++------------------------------------ 1 file changed, 7 insertions(+), 36 deletions(-) diff --git a/radio/src/opentx.cpp b/radio/src/opentx.cpp index 6ce62a3f6..4d49662cf 100644 --- a/radio/src/opentx.cpp +++ b/radio/src/opentx.cpp @@ -1688,53 +1688,24 @@ int8_t getMovedSwitch() } } #else - // saves about 50 bytes flash // return delivers 1 to 3 for ID1 to ID3 // 4..8 for all other switches if changed to true // -4..-8 for all other switches if changed to false // 9 for Trainer switch if changed to true; Change to false is ignored - - swstate_t mask=0x80; + swstate_t mask = 0x80; for (uint8_t i=NUM_PSWITCH; i>1; i--) { bool prev; - // mask= (1<<(i-2)); - prev=(switches_states & mask); + prev = (switches_states & mask); // don't use getSwitch here to always get the proper value, even getSwitch manipulates - // bool next = getSwitch(i); - bool next = switchState((EnumKeys)(SW_BASE+i-1)); - if (prev!=next) { - if (((i3)) || next==true) - result = next ? i : -i; - if ((i<=3) && (result==0)) result=1; - switches_states ^= mask; - } - mask>>=1; - } //endfor - -/* - for (uint8_t i=NUM_PSWITCH; i>0; i--) { - bool prev; - swstate_t mask = 0; - if (i <= 3) { - prev = ((switches_states & 0x03) == (i-1)); - } - else { - mask = (1<<(i-2)); - prev = (switches_states & mask); - } - // don't use getSwitch here to always get the proper value, because getSwitch manipulates - // bool next = getSwitch(i); bool next = switchState((EnumKeys)(SW_BASE+i-1)); if (prev != next) { - if (i!=NUM_PSWITCH || next==true) + if (((i3)) || next==true) result = next ? i : -i; - if (mask) - switches_states ^= mask; - else { - switches_states = (switches_states & 0xFC) | (i-1); - } + if (i<=3 && result==0) result = 1; + switches_states ^= mask; } - } //endfor */ + mask >>= 1; + } #endif if ((tmr10ms_t)(get_tmr10ms() - s_move_last_time) > 10) From 9c38236a30139eefdafd3b06ea94540e8266e2cb Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Fri, 21 Feb 2014 17:50:34 +0100 Subject: [PATCH 44/89] Another bug in system prompts referencing --- radio/src/audio_arm.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/radio/src/audio_arm.cpp b/radio/src/audio_arm.cpp index b1229f1cc..4ecc3f499 100644 --- a/radio/src/audio_arm.cpp +++ b/radio/src/audio_arm.cpp @@ -151,7 +151,7 @@ char * getSystemAudioPath(char * path) void getSystemAudioFile(char * filename, int index) { - char * str = getAudioPath(filename); + char * str = getSystemAudioPath(filename); strcpy(str, audioFilenames[index]); strcat(str, SOUNDS_EXT); } From 92a5429ce0b5c8c58b0d9e4bf1e124c505476242 Mon Sep 17 00:00:00 2001 From: Andre Bernet Date: Fri, 21 Feb 2014 23:22:06 +0100 Subject: [PATCH 45/89] Longer inhibition time for automatic switch prompts at power up --- radio/src/audio_arm.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/radio/src/audio_arm.cpp b/radio/src/audio_arm.cpp index 4ecc3f499..8e9f4a741 100644 --- a/radio/src/audio_arm.cpp +++ b/radio/src/audio_arm.cpp @@ -360,7 +360,7 @@ tmr10ms_t timeAutomaticPromptsSilence = 0; void playModelEvent(uint8_t category, uint8_t index, uint8_t event) { char filename[AUDIO_FILENAME_MAXLEN+1]; - if ((get_tmr10ms()-timeAutomaticPromptsSilence > 10) && isAudioFileReferenced((category << 24) + (index << 16) + event, filename)) { + if ((get_tmr10ms()-timeAutomaticPromptsSilence > 50) && isAudioFileReferenced((category << 24) + (index << 16) + event, filename)) { audioQueue.playFile(filename); } } From 82e74a72e6afc6b33d3db52070e1112802bd1443 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Sat, 22 Feb 2014 11:13:42 +0100 Subject: [PATCH 46/89] Shift in sources when 7 Lua scripts allowed --- companion/src/firmwares/opentx/opentxeeprom.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/companion/src/firmwares/opentx/opentxeeprom.cpp b/companion/src/firmwares/opentx/opentxeeprom.cpp index 3b3259803..ef971d41e 100644 --- a/companion/src/firmwares/opentx/opentxeeprom.cpp +++ b/companion/src/firmwares/opentx/opentxeeprom.cpp @@ -164,7 +164,7 @@ class SourcesConversionTable: public ConversionTable { if (IS_TARANIS(board) && version >= 216) { for (int i=0; i<32; i++) addConversion(RawSource(SOURCE_TYPE_VIRTUAL_INPUT, i), val++); - for (int i=0; i<3; i++) { + for (int i=0; i<7; i++) { for (int j=0; j<6; j++) { addConversion(RawSource(SOURCE_TYPE_LUA_INPUT, i*16+j), val++); } From f3b9135a09becce7d32440a9ae7351cfcbdfc876 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Sat, 22 Feb 2014 12:32:28 +0100 Subject: [PATCH 47/89] Core in Custom Functions Panel --- companion/src/modeledit/customfunctions.cpp | 30 +++++++++++---------- 1 file changed, 16 insertions(+), 14 deletions(-) diff --git a/companion/src/modeledit/customfunctions.cpp b/companion/src/modeledit/customfunctions.cpp index c9ba53ba5..b1805df46 100644 --- a/companion/src/modeledit/customfunctions.cpp +++ b/companion/src/modeledit/customfunctions.cpp @@ -162,7 +162,8 @@ CustomFunctionsPanel::CustomFunctionsPanel(QWidget * parent, ModelData & model, #ifdef PHONON playBT[i] = new QPushButton(this); - playBT[i]->setObjectName(QString("play_%1").arg(i)); + playBT[i]->setProperty("index", i); + playBT[i]->setProperty("state", "play"); playBT[i]->setIcon(CompanionIcon("play.png")); paramLayout->addWidget(playBT[i]); connect(playBT[i], SIGNAL(pressed()), this, SLOT(playMusic())); @@ -222,42 +223,43 @@ void CustomFunctionsPanel::mediaPlayer_state(Phonon::State newState, Phonon::Sta void CustomFunctionsPanel::playMusic() { - QPushButton *playButton = qobject_cast(sender()); - int index=playButton->objectName().mid(5,2).toInt(); - QString function=playButton->objectName().left(4); - QString path = g.profile[g.id()].sdPath(); + QPushButton * button = qobject_cast(sender()); + int index = button->property("index").toInt(); + QString function = button->property("state").toString(); + QString path = g.profile[g.id()].sdPath(); QDir qd(path); QString track; if (qd.exists()) { if (GetEepromInterface()->getCapability(VoicesAsNumbers)) { - track=path+QString("/%1.wav").arg(int(fswtchParam[index]->value()),4,10,(const QChar)'0'); + track = path + QString("/%1.wav").arg(int(fswtchParam[index]->value()), 4, 10, (const QChar)'0'); } else { path.append("/SOUNDS/"); QString lang = generalSettings.ttsLanguage; if (lang.isEmpty()) - lang="en"; + lang = "en"; path.append(lang); - if (fswtchParamArmT[index]->currentText()!="----") { - track=path+"/"+fswtchParamArmT[index]->currentText()+".wav"; + if (fswtchParamArmT[index]->currentText() != "----") { + track = path + "/" + fswtchParamArmT[index]->currentText() + ".wav"; } } QFile file(track); if (!file.exists()) { QMessageBox::critical(this, tr("Error"), tr("Unable to find sound file %1!").arg(track)); - track.clear(); + return; } #ifdef PHONON - if (function=="play" && !track.isEmpty()) { + if (function=="play") { clickObject->clear(); clickObject->setCurrentSource(Phonon::MediaSource(track)); clickObject->play(); - playBT[index]->setObjectName(QString("stop_%1").arg(index)); + playBT[index]->setProperty("state", "stop"); playBT[index]->setIcon(CompanionIcon("stop.png")); - } else { + } + else { clickObject->stop(); clickObject->clear(); - playBT[index]->setObjectName(QString("play_%1").arg(index)); + playBT[index]->setProperty("state", "play"); playBT[index]->setIcon(CompanionIcon("play.png")); } #endif From 10a1250496a20b3e42b5f919e09c9fbb1902037f Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Sat, 22 Feb 2014 19:55:18 +0100 Subject: [PATCH 48/89] I like these harmonics (63000, 0, 20000, 0, 20000) --- radio/src/audio_arm.cpp | 207 ++++++++++++++++++++-------------------- radio/util/sinus.py | 2 +- 2 files changed, 104 insertions(+), 105 deletions(-) diff --git a/radio/src/audio_arm.cpp b/radio/src/audio_arm.cpp index 7a2bb3468..139b17f45 100644 --- a/radio/src/audio_arm.cpp +++ b/radio/src/audio_arm.cpp @@ -41,110 +41,109 @@ extern OS_MutexID audioMutex; const int16_t sineValues[] = { - 0, 763, 1527, 2289, 3050, 3810, 4567, 5322, 6073, 6821, - 7565, 8305, 9039, 9769, 10493, 11211, 11922, 12626, 13324, 14013, - 14695, 15368, 16032, 16688, 17333, 17969, 18595, 19210, 19814, 20408, - 20989, 21559, 22117, 22663, 23196, 23716, 24223, 24717, 25197, 25664, - 26116, 26555, 26979, 27388, 27783, 28163, 28529, 28879, 29214, 29534, - 29838, 30127, 30401, 30659, 30901, 31128, 31340, 31535, 31716, 31880, - 32029, 32163, 32281, 32384, 32472, 32545, 32602, 32645, 32673, 32686, - 32685, 32670, 32640, 32596, 32539, 32468, 32384, 32287, 32176, 32054, - 31918, 31771, 31612, 31441, 31259, 31066, 30863, 30649, 30424, 30191, - 29947, 29695, 29434, 29165, 28887, 28602, 28309, 28010, 27704, 27392, - 27074, 26750, 26421, 26088, 25750, 25408, 25063, 24715, 24363, 24010, - 23654, 23296, 22938, 22578, 22218, 21857, 21497, 21138, 20779, 20422, - 20067, 19713, 19362, 19013, 18668, 18326, 17988, 17653, 17324, 16998, - 16678, 16363, 16054, 15750, 15453, 15162, 14877, 14600, 14329, 14066, - 13811, 13563, 13324, 13092, 12869, 12654, 12449, 12252, 12064, 11885, - 11715, 11555, 11404, 11263, 11132, 11010, 10898, 10796, 10704, 10622, - 10549, 10487, 10435, 10392, 10359, 10337, 10324, 10321, 10327, 10344, - 10369, 10405, 10449, 10503, 10566, 10638, 10719, 10808, 10906, 11013, - 11127, 11250, 11380, 11518, 11664, 11816, 11976, 12142, 12315, 12495, - 12680, 12871, 13067, 13269, 13476, 13688, 13904, 14124, 14348, 14576, - 14807, 15041, 15278, 15517, 15759, 16002, 16247, 16493, 16740, 16988, - 17236, 17484, 17732, 17979, 18225, 18471, 18714, 18957, 19197, 19435, - 19670, 19902, 20132, 20358, 20580, 20798, 21013, 21222, 21427, 21628, - 21823, 22012, 22196, 22375, 22547, 22713, 22873, 23026, 23172, 23311, - 23444, 23569, 23687, 23797, 23899, 23994, 24081, 24160, 24231, 24293, - 24348, 24394, 24432, 24461, 24483, 24495, 24500, 24495, 24483, 24461, - 24432, 24394, 24348, 24293, 24231, 24160, 24081, 23994, 23899, 23797, - 23687, 23569, 23444, 23311, 23172, 23026, 22873, 22713, 22547, 22375, - 22196, 22012, 21823, 21628, 21427, 21222, 21013, 20798, 20580, 20358, - 20132, 19902, 19670, 19435, 19197, 18957, 18714, 18471, 18225, 17979, - 17732, 17484, 17236, 16988, 16740, 16493, 16247, 16002, 15759, 15517, - 15278, 15041, 14807, 14576, 14348, 14124, 13904, 13688, 13476, 13269, - 13067, 12871, 12680, 12495, 12315, 12142, 11976, 11816, 11664, 11518, - 11380, 11250, 11127, 11013, 10906, 10808, 10719, 10638, 10566, 10503, - 10449, 10405, 10369, 10344, 10327, 10321, 10324, 10337, 10359, 10392, - 10435, 10487, 10549, 10622, 10704, 10796, 10898, 11010, 11132, 11263, - 11404, 11555, 11715, 11885, 12064, 12252, 12449, 12654, 12869, 13092, - 13324, 13563, 13811, 14066, 14329, 14600, 14877, 15162, 15453, 15750, - 16054, 16363, 16678, 16998, 17324, 17653, 17988, 18326, 18668, 19013, - 19362, 19713, 20067, 20422, 20779, 21138, 21497, 21857, 22218, 22578, - 22938, 23296, 23654, 24010, 24363, 24715, 25063, 25408, 25750, 26088, - 26421, 26750, 27074, 27392, 27704, 28010, 28309, 28602, 28887, 29165, - 29434, 29695, 29947, 30191, 30424, 30649, 30863, 31066, 31259, 31441, - 31612, 31771, 31918, 32054, 32176, 32287, 32384, 32468, 32539, 32596, - 32640, 32670, 32685, 32686, 32673, 32645, 32602, 32545, 32472, 32384, - 32281, 32163, 32029, 31880, 31716, 31535, 31340, 31128, 30901, 30659, - 30401, 30127, 29838, 29534, 29214, 28879, 28529, 28163, 27783, 27388, - 26979, 26555, 26116, 25664, 25197, 24717, 24223, 23716, 23196, 22663, - 22117, 21559, 20989, 20408, 19814, 19210, 18595, 17969, 17333, 16688, - 16032, 15368, 14695, 14013, 13324, 12626, 11922, 11211, 10493, 9769, - 9039, 8305, 7565, 6821, 6073, 5322, 4567, 3810, 3050, 2289, - 1527, 763, 0, -763, -1527, -2289, -3050, -3810, -4567, -5322, - -6073, -6821, -7565, -8305, -9039, -9769, -10493, -11211, -11922, -12626, - -13324, -14013, -14695, -15368, -16032, -16688, -17333, -17969, -18595, -19210, - -19814, -20408, -20989, -21559, -22117, -22663, -23196, -23716, -24223, -24717, - -25197, -25664, -26116, -26555, -26979, -27388, -27783, -28163, -28529, -28879, - -29214, -29534, -29838, -30127, -30401, -30659, -30901, -31128, -31340, -31535, - -31716, -31880, -32029, -32163, -32281, -32384, -32472, -32545, -32602, -32645, - -32673, -32686, -32685, -32670, -32640, -32596, -32539, -32468, -32384, -32287, - -32176, -32054, -31918, -31771, -31612, -31441, -31259, -31066, -30863, -30649, - -30424, -30191, -29947, -29695, -29434, -29165, -28887, -28602, -28309, -28010, - -27704, -27392, -27074, -26750, -26421, -26088, -25750, -25408, -25063, -24715, - -24363, -24010, -23654, -23296, -22938, -22578, -22218, -21857, -21497, -21138, - -20779, -20422, -20067, -19713, -19362, -19013, -18668, -18326, -17988, -17653, - -17324, -16998, -16678, -16363, -16054, -15750, -15453, -15162, -14877, -14600, - -14329, -14066, -13811, -13563, -13324, -13092, -12869, -12654, -12449, -12252, - -12064, -11885, -11715, -11555, -11404, -11263, -11132, -11010, -10898, -10796, - -10704, -10622, -10549, -10487, -10435, -10392, -10359, -10337, -10324, -10321, - -10327, -10344, -10369, -10405, -10449, -10503, -10566, -10638, -10719, -10808, - -10906, -11013, -11127, -11250, -11380, -11518, -11664, -11816, -11976, -12142, - -12315, -12495, -12680, -12871, -13067, -13269, -13476, -13688, -13904, -14124, - -14348, -14576, -14807, -15041, -15278, -15517, -15759, -16002, -16247, -16493, - -16740, -16988, -17236, -17484, -17732, -17979, -18225, -18471, -18714, -18957, - -19197, -19435, -19670, -19902, -20132, -20358, -20580, -20798, -21013, -21222, - -21427, -21628, -21823, -22012, -22196, -22375, -22547, -22713, -22873, -23026, - -23172, -23311, -23444, -23569, -23687, -23797, -23899, -23994, -24081, -24160, - -24231, -24293, -24348, -24394, -24432, -24461, -24483, -24495, -24500, -24495, - -24483, -24461, -24432, -24394, -24348, -24293, -24231, -24160, -24081, -23994, - -23899, -23797, -23687, -23569, -23444, -23311, -23172, -23026, -22873, -22713, - -22547, -22375, -22196, -22012, -21823, -21628, -21427, -21222, -21013, -20798, - -20580, -20358, -20132, -19902, -19670, -19435, -19197, -18957, -18714, -18471, - -18225, -17979, -17732, -17484, -17236, -16988, -16740, -16493, -16247, -16002, - -15759, -15517, -15278, -15041, -14807, -14576, -14348, -14124, -13904, -13688, - -13476, -13269, -13067, -12871, -12680, -12495, -12315, -12142, -11976, -11816, - -11664, -11518, -11380, -11250, -11127, -11013, -10906, -10808, -10719, -10638, - -10566, -10503, -10449, -10405, -10369, -10344, -10327, -10321, -10324, -10337, - -10359, -10392, -10435, -10487, -10549, -10622, -10704, -10796, -10898, -11010, - -11132, -11263, -11404, -11555, -11715, -11885, -12064, -12252, -12449, -12654, - -12869, -13092, -13324, -13563, -13811, -14066, -14329, -14600, -14877, -15162, - -15453, -15750, -16054, -16363, -16678, -16998, -17324, -17653, -17988, -18326, - -18668, -19013, -19362, -19713, -20067, -20422, -20779, -21138, -21497, -21857, - -22218, -22578, -22938, -23296, -23654, -24010, -24363, -24715, -25063, -25408, - -25750, -26088, -26421, -26750, -27074, -27392, -27704, -28010, -28309, -28602, - -28887, -29165, -29434, -29695, -29947, -30191, -30424, -30649, -30863, -31066, - -31259, -31441, -31612, -31771, -31918, -32054, -32176, -32287, -32384, -32468, - -32539, -32596, -32640, -32670, -32685, -32686, -32673, -32645, -32602, -32545, - -32472, -32384, -32281, -32163, -32029, -31880, -31716, -31535, -31340, -31128, - -30901, -30659, -30401, -30127, -29838, -29534, -29214, -28879, -28529, -28163, - -27783, -27388, -26979, -26555, -26116, -25664, -25197, -24717, -24223, -23716, - -23196, -22663, -22117, -21559, -20989, -20408, -19814, -19210, -18595, -17969, - -17333, -16688, -16032, -15368, -14695, -14013, -13324, -12626, -11922, -11211, - -10493, -9769, -9039, -8305, -7565, -6821, -6073, -5322, -4567, -3810, - -3050, -2289, -1527, -763, - + 0, 684, 1367, 2050, 2732, 3413, 4092, 4768, 5442, 6113, + 6782, 7446, 8107, 8763, 9415, 10062, 10704, 11340, 11970, 12595, + 13212, 13823, 14427, 15024, 15613, 16194, 16766, 17330, 17886, 18432, + 18970, 19497, 20015, 20523, 21021, 21509, 21986, 22452, 22907, 23351, + 23784, 24206, 24616, 25014, 25400, 25775, 26137, 26487, 26825, 27151, + 27464, 27765, 28053, 28329, 28592, 28843, 29081, 29306, 29519, 29719, + 29906, 30081, 30244, 30394, 30532, 30657, 30770, 30872, 30961, 31038, + 31104, 31157, 31200, 31231, 31251, 31260, 31258, 31245, 31222, 31188, + 31144, 31091, 31027, 30955, 30873, 30782, 30682, 30574, 30457, 30333, + 30200, 30061, 29914, 29760, 29599, 29432, 29259, 29080, 28895, 28706, + 28511, 28312, 28108, 27900, 27689, 27474, 27256, 27035, 26812, 26586, + 26359, 26130, 25899, 25668, 25436, 25203, 24971, 24738, 24506, 24275, + 24045, 23816, 23588, 23363, 23140, 22919, 22701, 22485, 22273, 22065, + 21860, 21659, 21462, 21269, 21081, 20898, 20719, 20546, 20378, 20216, + 20059, 19909, 19764, 19626, 19494, 19368, 19249, 19137, 19032, 18934, + 18842, 18758, 18681, 18612, 18550, 18495, 18448, 18408, 18376, 18351, + 18334, 18324, 18322, 18328, 18341, 18362, 18390, 18426, 18469, 18519, + 18577, 18641, 18713, 18792, 18878, 18970, 19070, 19176, 19288, 19406, + 19531, 19662, 19798, 19941, 20088, 20242, 20400, 20563, 20731, 20904, + 21081, 21263, 21448, 21637, 21830, 22026, 22226, 22428, 22633, 22840, + 23050, 23261, 23475, 23690, 23906, 24123, 24342, 24560, 24779, 24998, + 25217, 25436, 25654, 25871, 26087, 26302, 26515, 26726, 26935, 27142, + 27347, 27549, 27747, 27943, 28135, 28324, 28509, 28690, 28867, 29039, + 29207, 29370, 29528, 29681, 29829, 29972, 30109, 30240, 30365, 30484, + 30598, 30705, 30805, 30899, 30987, 31068, 31142, 31210, 31270, 31324, + 31370, 31410, 31442, 31467, 31485, 31496, 31500, 31496, 31485, 31467, + 31442, 31410, 31370, 31324, 31270, 31210, 31142, 31068, 30987, 30899, + 30805, 30705, 30598, 30484, 30365, 30240, 30109, 29972, 29829, 29681, + 29528, 29370, 29207, 29039, 28867, 28690, 28509, 28324, 28135, 27943, + 27747, 27549, 27347, 27142, 26935, 26726, 26515, 26302, 26087, 25871, + 25654, 25436, 25217, 24998, 24779, 24560, 24342, 24123, 23906, 23690, + 23475, 23261, 23050, 22840, 22633, 22428, 22226, 22026, 21830, 21637, + 21448, 21263, 21081, 20904, 20731, 20563, 20400, 20242, 20088, 19941, + 19798, 19662, 19531, 19406, 19288, 19176, 19070, 18970, 18878, 18792, + 18713, 18641, 18577, 18519, 18469, 18426, 18390, 18362, 18341, 18328, + 18322, 18324, 18334, 18351, 18376, 18408, 18448, 18495, 18550, 18612, + 18681, 18758, 18842, 18934, 19032, 19137, 19249, 19368, 19494, 19626, + 19764, 19909, 20059, 20216, 20378, 20546, 20719, 20898, 21081, 21269, + 21462, 21659, 21860, 22065, 22273, 22485, 22701, 22919, 23140, 23363, + 23588, 23816, 24045, 24275, 24506, 24738, 24971, 25203, 25436, 25668, + 25899, 26130, 26359, 26586, 26812, 27035, 27256, 27474, 27689, 27900, + 28108, 28312, 28511, 28706, 28895, 29080, 29259, 29432, 29599, 29760, + 29914, 30061, 30200, 30333, 30457, 30574, 30682, 30782, 30873, 30955, + 31027, 31091, 31144, 31188, 31222, 31245, 31258, 31260, 31251, 31231, + 31200, 31157, 31104, 31038, 30961, 30872, 30770, 30657, 30532, 30394, + 30244, 30081, 29906, 29719, 29519, 29306, 29081, 28843, 28592, 28329, + 28053, 27765, 27464, 27151, 26825, 26487, 26137, 25775, 25400, 25014, + 24616, 24206, 23784, 23351, 22907, 22452, 21986, 21509, 21021, 20523, + 20015, 19497, 18970, 18432, 17886, 17330, 16766, 16194, 15613, 15024, + 14427, 13823, 13212, 12595, 11970, 11340, 10704, 10062, 9415, 8763, + 8107, 7446, 6782, 6113, 5442, 4768, 4092, 3413, 2732, 2050, + 1367, 684, 0, -684, -1367, -2050, -2732, -3413, -4092, -4768, + -5442, -6113, -6782, -7446, -8107, -8763, -9415, -10062, -10704, -11340, + -11970, -12595, -13212, -13823, -14427, -15024, -15613, -16194, -16766, -17330, + -17886, -18432, -18970, -19497, -20015, -20523, -21021, -21509, -21986, -22452, + -22907, -23351, -23784, -24206, -24616, -25014, -25400, -25775, -26137, -26487, + -26825, -27151, -27464, -27765, -28053, -28329, -28592, -28843, -29081, -29306, + -29519, -29719, -29906, -30081, -30244, -30394, -30532, -30657, -30770, -30872, + -30961, -31038, -31104, -31157, -31200, -31231, -31251, -31260, -31258, -31245, + -31222, -31188, -31144, -31091, -31027, -30955, -30873, -30782, -30682, -30574, + -30457, -30333, -30200, -30061, -29914, -29760, -29599, -29432, -29259, -29080, + -28895, -28706, -28511, -28312, -28108, -27900, -27689, -27474, -27256, -27035, + -26812, -26586, -26359, -26130, -25899, -25668, -25436, -25203, -24971, -24738, + -24506, -24275, -24045, -23816, -23588, -23363, -23140, -22919, -22701, -22485, + -22273, -22065, -21860, -21659, -21462, -21269, -21081, -20898, -20719, -20546, + -20378, -20216, -20059, -19909, -19764, -19626, -19494, -19368, -19249, -19137, + -19032, -18934, -18842, -18758, -18681, -18612, -18550, -18495, -18448, -18408, + -18376, -18351, -18334, -18324, -18322, -18328, -18341, -18362, -18390, -18426, + -18469, -18519, -18577, -18641, -18713, -18792, -18878, -18970, -19070, -19176, + -19288, -19406, -19531, -19662, -19798, -19941, -20088, -20242, -20400, -20563, + -20731, -20904, -21081, -21263, -21448, -21637, -21830, -22026, -22226, -22428, + -22633, -22840, -23050, -23261, -23475, -23690, -23906, -24123, -24342, -24560, + -24779, -24998, -25217, -25436, -25654, -25871, -26087, -26302, -26515, -26726, + -26935, -27142, -27347, -27549, -27747, -27943, -28135, -28324, -28509, -28690, + -28867, -29039, -29207, -29370, -29528, -29681, -29829, -29972, -30109, -30240, + -30365, -30484, -30598, -30705, -30805, -30899, -30987, -31068, -31142, -31210, + -31270, -31324, -31370, -31410, -31442, -31467, -31485, -31496, -31500, -31496, + -31485, -31467, -31442, -31410, -31370, -31324, -31270, -31210, -31142, -31068, + -30987, -30899, -30805, -30705, -30598, -30484, -30365, -30240, -30109, -29972, + -29829, -29681, -29528, -29370, -29207, -29039, -28867, -28690, -28509, -28324, + -28135, -27943, -27747, -27549, -27347, -27142, -26935, -26726, -26515, -26302, + -26087, -25871, -25654, -25436, -25217, -24998, -24779, -24560, -24342, -24123, + -23906, -23690, -23475, -23261, -23050, -22840, -22633, -22428, -22226, -22026, + -21830, -21637, -21448, -21263, -21081, -20904, -20731, -20563, -20400, -20242, + -20088, -19941, -19798, -19662, -19531, -19406, -19288, -19176, -19070, -18970, + -18878, -18792, -18713, -18641, -18577, -18519, -18469, -18426, -18390, -18362, + -18341, -18328, -18322, -18324, -18334, -18351, -18376, -18408, -18448, -18495, + -18550, -18612, -18681, -18758, -18842, -18934, -19032, -19137, -19249, -19368, + -19494, -19626, -19764, -19909, -20059, -20216, -20378, -20546, -20719, -20898, + -21081, -21269, -21462, -21659, -21860, -22065, -22273, -22485, -22701, -22919, + -23140, -23363, -23588, -23816, -24045, -24275, -24506, -24738, -24971, -25203, + -25436, -25668, -25899, -26130, -26359, -26586, -26812, -27035, -27256, -27474, + -27689, -27900, -28108, -28312, -28511, -28706, -28895, -29080, -29259, -29432, + -29599, -29760, -29914, -30061, -30200, -30333, -30457, -30574, -30682, -30782, + -30873, -30955, -31027, -31091, -31144, -31188, -31222, -31245, -31258, -31260, + -31251, -31231, -31200, -31157, -31104, -31038, -30961, -30872, -30770, -30657, + -30532, -30394, -30244, -30081, -29906, -29719, -29519, -29306, -29081, -28843, + -28592, -28329, -28053, -27765, -27464, -27151, -26825, -26487, -26137, -25775, + -25400, -25014, -24616, -24206, -23784, -23351, -22907, -22452, -21986, -21509, + -21021, -20523, -20015, -19497, -18970, -18432, -17886, -17330, -16766, -16194, + -15613, -15024, -14427, -13823, -13212, -12595, -11970, -11340, -10704, -10062, + -9415, -8763, -8107, -7446, -6782, -6113, -5442, -4768, -4092, -3413, + -2732, -2050, -1367, -684, }; #if defined(SDCARD) diff --git a/radio/util/sinus.py b/radio/util/sinus.py index e852b7427..0754c4447 100644 --- a/radio/util/sinus.py +++ b/radio/util/sinus.py @@ -3,7 +3,7 @@ import math samples = 1024 -amplitudes = (49000, 0, 25000, 0, 25000) +amplitudes = (63000, 0, 20000, 0, 20000) max = 0 min = 0 From c63a29ef97dd9a1259311f265538bf32590e4f45 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Sat, 22 Feb 2014 19:57:25 +0100 Subject: [PATCH 49/89] Debug mods removed for pull request --- radio/src/maths.cpp | 2 +- radio/src/telemetry/frsky_sport.cpp | 7 ++----- 2 files changed, 3 insertions(+), 6 deletions(-) diff --git a/radio/src/maths.cpp b/radio/src/maths.cpp index 7010444a5..63e57eaeb 100644 --- a/radio/src/maths.cpp +++ b/radio/src/maths.cpp @@ -124,7 +124,7 @@ void varioWakeup() int verticalSpeed = frskyData.hub.varioSpeed; -#if defined(PCBTARANIS) +#if 0 if (g_model.frsky.varioSource == VARIO_SOURCE_DTE) { #warning "Ele stick for vario tests" verticalSpeed = getValue(MIXSRC_Ele); diff --git a/radio/src/telemetry/frsky_sport.cpp b/radio/src/telemetry/frsky_sport.cpp index beb852cdf..646dd2246 100644 --- a/radio/src/telemetry/frsky_sport.cpp +++ b/radio/src/telemetry/frsky_sport.cpp @@ -654,12 +654,9 @@ void telemetryWakeup() #endif #if defined(VARIO) -#if 1 - #warning "test removed for vario tests" -#else - if (TELEMETRY_STREAMING() && !IS_FAI_ENABLED()) -#endif + if (TELEMETRY_STREAMING() && !IS_FAI_ENABLED()) { varioWakeup(); + } #endif static tmr10ms_t alarmsCheckTime = 0; From 62f921404ee5625bdba4e6a1eca817c3554f68f4 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Sun, 23 Feb 2014 09:22:51 +0100 Subject: [PATCH 50/89] Indication of current flight mode in global vars - 1st part: the 2 seconds --- radio/src/gui/menu_model.cpp | 10 +++++++++- radio/src/gui/menus.cpp | 8 ++++++++ radio/src/gui/menus.h | 4 ++++ 3 files changed, 21 insertions(+), 1 deletion(-) diff --git a/radio/src/gui/menu_model.cpp b/radio/src/gui/menu_model.cpp index d1dd68a46..527f147a0 100644 --- a/radio/src/gui/menu_model.cpp +++ b/radio/src/gui/menu_model.cpp @@ -4087,7 +4087,15 @@ void onGVARSMenu(const char *result) void menuModelGVars(uint8_t event) { - MENU(STR_MENUGLOBALVARS, menuTabModel, e_GVars, 1+MAX_GVARS, {0, NAVIGATION_LINE_BY_LINE|MAX_PHASES, NAVIGATION_LINE_BY_LINE|MAX_PHASES, NAVIGATION_LINE_BY_LINE|MAX_PHASES, NAVIGATION_LINE_BY_LINE|MAX_PHASES, NAVIGATION_LINE_BY_LINE|MAX_PHASES, NAVIGATION_LINE_BY_LINE|MAX_PHASES, NAVIGATION_LINE_BY_LINE|MAX_PHASES, NAVIGATION_LINE_BY_LINE|MAX_PHASES, NAVIGATION_LINE_BY_LINE|MAX_PHASES}); + tmr10ms_t tmr10ms = get_tmr10ms(); + const char * menuTitle; + + if (tmr10ms - menuEntryTime > 200/*2 seconds*/) + menuTitle = "GLOBAL V."; // TODO translate + else + menuTitle = STR_MENUGLOBALVARS; + + MENU(menuTitle, menuTabModel, e_GVars, 1+MAX_GVARS, {0, NAVIGATION_LINE_BY_LINE|MAX_PHASES, NAVIGATION_LINE_BY_LINE|MAX_PHASES, NAVIGATION_LINE_BY_LINE|MAX_PHASES, NAVIGATION_LINE_BY_LINE|MAX_PHASES, NAVIGATION_LINE_BY_LINE|MAX_PHASES, NAVIGATION_LINE_BY_LINE|MAX_PHASES, NAVIGATION_LINE_BY_LINE|MAX_PHASES, NAVIGATION_LINE_BY_LINE|MAX_PHASES, NAVIGATION_LINE_BY_LINE|MAX_PHASES}); uint8_t sub = m_posVert - 1; diff --git a/radio/src/gui/menus.cpp b/radio/src/gui/menus.cpp index dfc74980e..51577c47a 100644 --- a/radio/src/gui/menus.cpp +++ b/radio/src/gui/menus.cpp @@ -358,6 +358,10 @@ void onLongMenuPress(const char *result) } #endif +#if defined(CPUARM) +tmr10ms_t menuEntryTime; +#endif + bool check(check_event_t event, uint8_t curr, const MenuFuncP *menuTab, uint8_t menuTabSize, const pm_uint8_t *horTab, uint8_t horTabMax, vertpos_t maxrow) { vertpos_t l_posVert = m_posVert; @@ -522,6 +526,9 @@ bool check(check_event_t event, uint8_t curr, const MenuFuncP *menuTab, uint8_t switch(event) { case EVT_ENTRY: +#if defined(CPUARM) + menuEntryTime = get_tmr10ms(); +#endif l_posVert = POS_VERT_INIT; l_posHorz = POS_HORZ_INIT(l_posVert); SET_SCROLLBAR_X(LCD_W-1); @@ -538,6 +545,7 @@ bool check(check_event_t event, uint8_t curr, const MenuFuncP *menuTab, uint8_t #if defined(PCBTARANIS) case EVT_ENTRY_UP: + menuEntryTime = get_tmr10ms(); s_editMode = 0; l_posHorz = POS_HORZ_INIT(l_posVert); SET_SCROLLBAR_X(LCD_W-1); diff --git a/radio/src/gui/menus.h b/radio/src/gui/menus.h index 02ae64ca6..479be9039 100644 --- a/radio/src/gui/menus.h +++ b/radio/src/gui/menus.h @@ -88,6 +88,10 @@ inline void displayColumnHeader(const char **headers, uint8_t index) #define horzpos_t uint8_t #endif +#if defined(CPUARM) + extern tmr10ms_t menuEntryTime; +#endif + extern vertpos_t m_posVert; extern horzpos_t m_posHorz; extern vertpos_t s_pgOfs; From 7195ad38066a2586fe8e67f755d49183f6de6baa Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Sun, 23 Feb 2014 09:54:12 +0100 Subject: [PATCH 51/89] The headers in the top bar - still the page number to remove! --- radio/src/gui/menu_model.cpp | 13 ++++++++++--- 1 file changed, 10 insertions(+), 3 deletions(-) diff --git a/radio/src/gui/menu_model.cpp b/radio/src/gui/menu_model.cpp index 527f147a0..1b812eee7 100644 --- a/radio/src/gui/menu_model.cpp +++ b/radio/src/gui/menu_model.cpp @@ -4085,15 +4085,22 @@ void onGVARSMenu(const char *result) } } +#define GVARS_FM_COLUMN(p) (12*FW + FWNUM + (p)*(2+3*FWNUM) - 3) + void menuModelGVars(uint8_t event) { tmr10ms_t tmr10ms = get_tmr10ms(); const char * menuTitle; - if (tmr10ms - menuEntryTime > 200/*2 seconds*/) + if (tmr10ms - menuEntryTime > 200/*2 seconds*/) { menuTitle = "GLOBAL V."; // TODO translate - else + for (int i=0; i0) ? BLINK|INVERS : INVERS) : 0); - xcoord_t x = 12*FW + FWNUM + (j-1)*(2+3*FWNUM) - 3; + xcoord_t x = GVARS_FM_COLUMN(j-1); #if MAX_GVARS == 6 if (i==0 && j!=9) putsStrIdx(x+2, FH+1, STR_FP, j, SMLSIZE); From ed6fc15a13a538a9eb3815c00ea5cbce2ab533ee Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Sun, 23 Feb 2014 19:09:17 +0100 Subject: [PATCH 52/89] Screen index hidden on GVARS screen (after 2 seconds) --- radio/src/gui/menu_model.cpp | 5 +- radio/src/gui/menus.cpp | 404 +++++++++++++++++++++++------------ radio/src/gui/menus.h | 17 +- 3 files changed, 291 insertions(+), 135 deletions(-) diff --git a/radio/src/gui/menu_model.cpp b/radio/src/gui/menu_model.cpp index 1b812eee7..427634daa 100644 --- a/radio/src/gui/menu_model.cpp +++ b/radio/src/gui/menu_model.cpp @@ -4091,8 +4091,9 @@ void menuModelGVars(uint8_t event) { tmr10ms_t tmr10ms = get_tmr10ms(); const char * menuTitle; + bool first2seconds = (tmr10ms - menuEntryTime > 200); /*2 seconds*/ - if (tmr10ms - menuEntryTime > 200/*2 seconds*/) { + if (first2seconds) { menuTitle = "GLOBAL V."; // TODO translate for (int i=0; i scroll values - static int16_t p1val; - static int16_t p1valprev; - p1valdiff = (p1val-calibratedStick[6]) / SCROLL_POT1_TH; - if (p1valdiff) { - p1valdiff = (p1valprev-calibratedStick[6]) / 2; - p1val = calibratedStick[6]; - } - p1valprev = calibratedStick[6]; -#endif - -#ifdef NAVIGATION_POT2 - // check pot 2 - if changed -> scroll menu - static int16_t p2valprev; - p2valdiff = (p2valprev-calibratedStick[4]) / SCROLL_TH; - if (p2valdiff) p2valprev = calibratedStick[4]; -#endif - -#ifdef NAVIGATION_POT3 - // check pot 3 if changed -> cursor down/up - static int16_t p3valprev; - int8_t scrollUD = (p3valprev-calibratedStick[5]) / SCROLL_TH; - if (scrollUD) p3valprev = calibratedStick[5]; -#else #define scrollUD 0 -#endif if (p2valdiff || scrollUD || p1valdiff) backlightOn(); // on keypress turn the light on if (menuTab) { uint8_t attr = 0; -#if defined(PCBTARANIS) int8_t cc = curr; switch(event) { case EVT_KEY_LONG(KEY_MENU): @@ -439,7 +413,271 @@ bool check(check_event_t event, uint8_t curr, const MenuFuncP *menuTab, uint8_t chainMenu((MenuFuncP)pgm_read_adr(&menuTab[cc])); return false; } + + s_noScroll = 0; + + if (!(flags&CHECK_FLAG_NO_SCREEN_INDEX)) { + displayScreenIndex(curr, menuTabSize, attr); + } + + lcd_filled_rect(0, 0, LCD_W, FH, SOLID, FILL_WHITE|GREY_DEFAULT); + } + + DISPLAY_PROGRESS_BAR(menuTab ? lcdLastPos-2*FW-((curr+1)/10*FWNUM)-2 : 20*FW+1); + + if (s_editMode<=0) { + if (scrollUD) { + l_posVert = limit((int8_t)0, (int8_t)(l_posVert - scrollUD), (int8_t)maxrow); + l_posHorz = min((uint8_t)l_posHorz, MAXCOL(l_posVert)); + } + + if (p2valdiff && l_posVert>0) { + l_posHorz = limit((int8_t)0, (int8_t)((uint8_t)l_posHorz - p2valdiff), (int8_t)maxcol); + } + } + + switch(event) + { + case EVT_ENTRY: + menuEntryTime = get_tmr10ms(); + l_posVert = POS_VERT_INIT; + l_posHorz = POS_HORZ_INIT(l_posVert); + SET_SCROLLBAR_X(LCD_W-1); +#if defined(ROTARY_ENCODER_NAVIGATION) + if (menuTab) { + s_editMode = EDIT_MODE_INIT; + break; + } + // no break #else + s_editMode = EDIT_MODE_INIT; + break; +#endif + + case EVT_ENTRY_UP: + menuEntryTime = get_tmr10ms(); + s_editMode = 0; + l_posHorz = POS_HORZ_INIT(l_posVert); + SET_SCROLLBAR_X(LCD_W-1); + break; + + case EVT_ROTARY_BREAK: + if (s_editMode > 1) break; + if (m_posHorz < 0 && maxcol > 0 && READ_ONLY_UNLOCKED()) { + l_posHorz = 0; + break; + } + if (!menuTab || l_posVert>0) { + if (READ_ONLY_UNLOCKED()) { + s_editMode = (s_editMode<=0); + } + } + break; + +#if defined(ROTARY_ENCODER_NAVIGATION) + case EVT_ROTARY_LONG: + if (s_editMode > 1) break; + killEvents(event); + if (l_posVert != POS_VERT_INIT) { + l_posVert = POS_VERT_INIT; + s_editMode = EDIT_MODE_INIT; + break; + } + // no break +#endif + case EVT_KEY_LONG(KEY_EXIT): + s_editMode = 0; // TODO needed? we call ENTRY_UP after which does the same + popMenu(); + return false; + + case EVT_KEY_BREAK(KEY_EXIT): +#if defined(ROTARY_ENCODER_NAVIGATION) + if (s_editMode == 0) + s_editMode = EDIT_MODE_INIT; + else +#endif + if (s_editMode>0) { + s_editMode = 0; + break; + } + + if (l_posHorz >= 0 && (COLATTR(l_posVert) & NAVIGATION_LINE_BY_LINE)) { + l_posHorz = -1; + } + else + { + uint8_t posVertInit = POS_VERT_INIT; + if (s_pgOfs != 0 || l_posVert != posVertInit) { + s_pgOfs = 0; + l_posVert = posVertInit; + l_posHorz = POS_HORZ_INIT(l_posVert); + } + else { + popMenu(); + return false; + } + } + break; + + CASE_EVT_ROTARY_MOVE_RIGHT + if (s_editMode != 0) break; + if ((COLATTR(l_posVert) & NAVIGATION_LINE_BY_LINE)) { + if (l_posHorz >= 0) { + INC(l_posHorz, 0, maxcol); + break; + } + } + else { + if (l_posHorz < maxcol) { + l_posHorz++; + break; + } + else { + l_posHorz = 0; + if (!IS_ROTARY_MOVE_RIGHT(event)) + break; + } + } + + do { + INC(l_posVert, POS_VERT_INIT, maxrow); + } while (CURSOR_NOT_ALLOWED_IN_ROW(l_posVert)); + + s_editMode = 0; // if we go down, we must be in this mode + + l_posHorz = POS_HORZ_INIT(l_posVert); + break; + + CASE_EVT_ROTARY_MOVE_LEFT + if (s_editMode != 0) break; + if ((COLATTR(l_posVert) & NAVIGATION_LINE_BY_LINE)) { + if (l_posHorz >= 0) { + DEC(l_posHorz, 0, maxcol); + break; + } + } + else { + if (l_posHorz > 0) { + l_posHorz--; + break; + } + else if (IS_ROTARY_MOVE_LEFT(event) && s_editMode == 0) { + l_posHorz = 0xff; + } + else { + l_posHorz = maxcol; + break; + } + } + + do { + DEC(l_posVert, POS_VERT_INIT, maxrow); + } while (CURSOR_NOT_ALLOWED_IN_ROW(l_posVert)); + + s_editMode = 0; // if we go up, we must be in this mode + + if ((COLATTR(l_posVert) & NAVIGATION_LINE_BY_LINE)) + l_posHorz = -1; + else + l_posHorz = min((uint8_t)l_posHorz, MAXCOL(l_posVert)); + + break; + } + +#if defined(CPUARM) + if (l_posVert<1) s_pgOfs=0; + else if (menuTab && horTab) { + vertpos_t realPosVert = l_posVert; + vertpos_t realPgOfs = s_pgOfs; + vertpos_t realMaxrow = maxrow; + for (vertpos_t i=1; i<=maxrow; i++) { + if (MAXCOL(i) == HIDDEN_ROW) { + realMaxrow--; + if (i < l_posVert) + realPosVert--; + if (i < s_pgOfs) + realPgOfs--; + } + } + if (realPosVert>(LCD_LINES-1)+realPgOfs) realPgOfs = realPosVert-(LCD_LINES-1); + else if (realPosVert<1+realPgOfs) realPgOfs = realPosVert-1; + s_pgOfs = realPgOfs; + for (vertpos_t i=1; i<=realPgOfs; i++) { + if (MAXCOL(i) == HIDDEN_ROW) { + s_pgOfs++; + } + } + maxrow = realMaxrow; + } + else { + uint8_t max = menuTab ? LCD_LINES-1 : LCD_LINES-2; + if (l_posVert>max+s_pgOfs) s_pgOfs = l_posVert-max; + else if (l_posVert<1+s_pgOfs) s_pgOfs = l_posVert-1; + } + +#if LCD_W >= 212 + if (maxrow > LCD_LINES-1 && scrollbar_X) + displayScrollbar(scrollbar_X, FH, LCD_H-FH, s_pgOfs, menuTab ? maxrow : maxrow+1, LCD_LINES-1); +#endif + +#else + uint8_t max = menuTab ? LCD_LINES-1 : LCD_LINES-2; + if (l_posVert<1) s_pgOfs=0; + else if (l_posVert>max+s_pgOfs) s_pgOfs = l_posVert-max; + else if (l_posVert<1+s_pgOfs) s_pgOfs = l_posVert-1; +#endif + m_posVert = l_posVert; + m_posHorz = l_posHorz; + if (s_pgOfs > 0) { + l_posVert--; + if (l_posVert == s_pgOfs && CURSOR_NOT_ALLOWED_IN_ROW(l_posVert)) + s_pgOfs = l_posVert-1; + } + return true; +} + +#else // defined(PCBTARANIS) + +bool check(check_event_t event, uint8_t curr, const MenuFuncP *menuTab, uint8_t menuTabSize, const pm_uint8_t *horTab, uint8_t horTabMax, vertpos_t maxrow) +{ + vertpos_t l_posVert = m_posVert; + horzpos_t l_posHorz = m_posHorz; + + uint8_t maxcol = MAXCOL(l_posVert); + +#if defined(NAVIGATION_POT1) + // check pot 1 - if changed -> scroll values + static int16_t p1val; + static int16_t p1valprev; + p1valdiff = (p1val-calibratedStick[6]) / SCROLL_POT1_TH; + if (p1valdiff) { + p1valdiff = (p1valprev-calibratedStick[6]) / 2; + p1val = calibratedStick[6]; + } + p1valprev = calibratedStick[6]; +#endif + +#if defined(NAVIGATION_POT2) + // check pot 2 - if changed -> scroll menu + static int16_t p2valprev; + p2valdiff = (p2valprev-calibratedStick[4]) / SCROLL_TH; + if (p2valdiff) p2valprev = calibratedStick[4]; +#endif + +#if defined(NAVIGATION_POT3) + // check pot 3 if changed -> cursor down/up + static int16_t p3valprev; + int8_t scrollUD = (p3valprev-calibratedStick[5]) / SCROLL_TH; + if (scrollUD) p3valprev = calibratedStick[5]; +#else + #define scrollUD 0 +#endif + + if (p2valdiff || scrollUD || p1valdiff) backlightOn(); // on keypress turn the light on + + if (menuTab) { + uint8_t attr = 0; + if (l_posVert==0 && !s_noScroll) { attr = INVERS; @@ -500,14 +738,10 @@ bool check(check_event_t event, uint8_t curr, const MenuFuncP *menuTab, uint8_t attr = INVERS|BLINK; #endif } -#endif s_noScroll = 0; displayScreenIndex(curr, menuTabSize, attr); -#if defined(PCBTARANIS) - lcd_filled_rect(0, 0, LCD_W, FH, SOLID, FILL_WHITE|GREY_DEFAULT); -#endif } DISPLAY_PROGRESS_BAR(menuTab ? lcdLastPos-2*FW-((curr+1)/10*FWNUM)-2 : 20*FW+1); @@ -543,21 +777,7 @@ bool check(check_event_t event, uint8_t curr, const MenuFuncP *menuTab, uint8_t break; #endif -#if defined(PCBTARANIS) - case EVT_ENTRY_UP: - menuEntryTime = get_tmr10ms(); - s_editMode = 0; - l_posHorz = POS_HORZ_INIT(l_posVert); - SET_SCROLLBAR_X(LCD_W-1); - break; - - case EVT_ROTARY_BREAK: - if (s_editMode > 1) break; - if (m_posHorz < 0 && maxcol > 0 && READ_ONLY_UNLOCKED()) { - l_posHorz = 0; - break; - } -#elif defined(ROTARY_ENCODER_NAVIGATION) +#if defined(ROTARY_ENCODER_NAVIGATION) case EVT_ENTRY_UP: s_editMode = 0; SET_SCROLLBAR_X(LCD_W-1); @@ -567,9 +787,7 @@ bool check(check_event_t event, uint8_t curr, const MenuFuncP *menuTab, uint8_t if (s_editMode > 1) break; #endif -#if !defined(PCBTARANIS) case EVT_KEY_FIRST(KEY_ENTER): -#endif if (!menuTab || l_posVert>0) { if (READ_ONLY_UNLOCKED()) { s_editMode = (s_editMode<=0); @@ -603,24 +821,7 @@ bool check(check_event_t event, uint8_t curr, const MenuFuncP *menuTab, uint8_t s_editMode = 0; break; } -#if defined(PCBTARANIS) - if (l_posHorz >= 0 && (COLATTR(l_posVert) & NAVIGATION_LINE_BY_LINE)) { - l_posHorz = -1; - } - else - { - uint8_t posVertInit = POS_VERT_INIT; - if (s_pgOfs != 0 || l_posVert != posVertInit) { - s_pgOfs = 0; - l_posVert = posVertInit; - l_posHorz = POS_HORZ_INIT(l_posVert); - } - else { - popMenu(); - return false; - } - } -#else + if (l_posVert==0 || !menuTab) { popMenu(); // beeps itself return false; @@ -630,39 +831,16 @@ bool check(check_event_t event, uint8_t curr, const MenuFuncP *menuTab, uint8_t l_posVert = 0; l_posHorz = 0; } -#endif break; -#if !defined(PCBTARANIS) case EVT_KEY_REPT(KEY_RIGHT): //inc if (l_posHorz==maxcol) break; // no break case EVT_KEY_FIRST(KEY_RIGHT)://inc if (!horTab || s_editMode>0) break; -#endif -#if defined(PCBTARANIS) - CASE_EVT_ROTARY_MOVE_RIGHT - if (s_editMode != 0) break; - if ((COLATTR(l_posVert) & NAVIGATION_LINE_BY_LINE)) { - if (l_posHorz >= 0) { - INC(l_posHorz, 0, maxcol); - break; - } - } - else { - if (l_posHorz < maxcol) { - l_posHorz++; - break; - } - else { - l_posHorz = 0; - if (!IS_ROTARY_MOVE_RIGHT(event)) - break; - } - } -#elif defined(ROTARY_ENCODER_NAVIGATION) +#if defined(ROTARY_ENCODER_NAVIGATION) CASE_EVT_ROTARY_MOVE_RIGHT if (s_editMode != 0) break; if (l_posHorz < maxcol) { @@ -679,61 +857,31 @@ bool check(check_event_t event, uint8_t curr, const MenuFuncP *menuTab, uint8_t break; #endif -#if !defined(PCBTARANIS) case EVT_KEY_REPT(KEY_DOWN): //inc if (!IS_ROTARY_RIGHT(event) && l_posVert==maxrow) break; // no break case EVT_KEY_FIRST(KEY_DOWN): //inc if (s_editMode>0) break; -#endif do { INC(l_posVert, POS_VERT_INIT, maxrow); } while (CURSOR_NOT_ALLOWED_IN_ROW(l_posVert)); -#if defined(ROTARY_ENCODER_NAVIGATION) || defined(PCBTARANIS) +#if defined(ROTARY_ENCODER_NAVIGATION) s_editMode = 0; // if we go down, we must be in this mode #endif -#if defined(PCBTARANIS) - l_posHorz = POS_HORZ_INIT(l_posVert); -#else l_posHorz = min(l_posHorz, MAXCOL(l_posVert)); -#endif break; -#if !defined(PCBTARANIS) case EVT_KEY_REPT(KEY_LEFT): //dec if (l_posHorz==0) break; // no break case EVT_KEY_FIRST(KEY_LEFT)://dec if (!horTab || s_editMode>0) break; -#endif -#if defined(PCBTARANIS) - CASE_EVT_ROTARY_MOVE_LEFT - if (s_editMode != 0) break; - if ((COLATTR(l_posVert) & NAVIGATION_LINE_BY_LINE)) { - if (l_posHorz >= 0) { - DEC(l_posHorz, 0, maxcol); - break; - } - } - else { - if (l_posHorz > 0) { - l_posHorz--; - break; - } - else if (IS_ROTARY_MOVE_LEFT(event) && s_editMode == 0) { - l_posHorz = 0xff; - } - else { - l_posHorz = maxcol; - break; - } - } -#elif defined(ROTARY_ENCODER_NAVIGATION) +#if defined(ROTARY_ENCODER_NAVIGATION) CASE_EVT_ROTARY_MOVE_LEFT if (s_editMode != 0) break; if (l_posHorz > 0) { @@ -752,13 +900,11 @@ bool check(check_event_t event, uint8_t curr, const MenuFuncP *menuTab, uint8_t break; #endif -#if !defined(PCBTARANIS) case EVT_KEY_REPT(KEY_UP): //dec if (!IS_ROTARY_LEFT(event) && l_posVert==0) break; // no break case EVT_KEY_FIRST(KEY_UP): //dec if (s_editMode>0) break; -#endif do { DEC(l_posVert, POS_VERT_INIT, maxrow); @@ -768,14 +914,7 @@ bool check(check_event_t event, uint8_t curr, const MenuFuncP *menuTab, uint8_t s_editMode = 0; // if we go up, we must be in this mode #endif -#if defined(PCBTARANIS) - if ((COLATTR(l_posVert) & NAVIGATION_LINE_BY_LINE)) - l_posHorz = -1; - else - l_posHorz = min((uint8_t)l_posHorz, MAXCOL(l_posVert)); -#else l_posHorz = min((uint8_t)l_posHorz, MAXCOL(l_posVert)); -#endif break; } @@ -833,6 +972,7 @@ bool check(check_event_t event, uint8_t curr, const MenuFuncP *menuTab, uint8_t #endif return true; } +#endif MenuFuncP g_menuStack[5]; uint8_t g_menuPos[4]; diff --git a/radio/src/gui/menus.h b/radio/src/gui/menus.h index 479be9039..fca197017 100644 --- a/radio/src/gui/menus.h +++ b/radio/src/gui/menus.h @@ -230,7 +230,14 @@ int8_t checkIncDecGen(uint8_t event, int8_t i_val, int8_t i_min, int8_t i_max); #else #define NAVIGATION_LINE_BY_LINE 0 #endif -bool check(check_event_t event, uint8_t curr, const MenuFuncP *menuTab, uint8_t menuTabSize, const pm_uint8_t *subTab, uint8_t subTabMax, vertpos_t maxrow); + +#if defined(PCBTARANIS) + #define CHECK_FLAG_NO_SCREEN_INDEX 1 + bool check(check_event_t event, uint8_t curr, const MenuFuncP *menuTab, uint8_t menuTabSize, const pm_uint8_t *horTab, uint8_t horTabMax, vertpos_t maxrow, uint8_t flags=0); +#else + bool check(check_event_t event, uint8_t curr, const MenuFuncP *menuTab, uint8_t menuTabSize, const pm_uint8_t *horTab, uint8_t horTabMax, vertpos_t maxrow); +#endif + bool check_simple(check_event_t event, uint8_t curr, const MenuFuncP *menuTab, uint8_t menuTabSize, vertpos_t maxrow); bool check_submenu_simple(check_event_t event, uint8_t maxrow); @@ -246,11 +253,19 @@ void title(const pm_char * s); #define MENU_CHECK(tab, menu, lines_count) \ check(event, menu, tab, DIM(tab), mstate_tab, DIM(mstate_tab)-1, (lines_count)-1) +#define MENU_CHECK_FLAGS(tab, menu, flags, lines_count) \ + check(event, menu, tab, DIM(tab), mstate_tab, DIM(mstate_tab)-1, (lines_count)-1, flags) + #define MENU(title, tab, menu, lines_count, ...) \ MENU_TAB(__VA_ARGS__); \ if (!MENU_CHECK(tab, menu, lines_count)) return; \ TITLE(title) +#define MENU_FLAGS(title, tab, menu, flags, lines_count, ...) \ + MENU_TAB(__VA_ARGS__); \ + if (!MENU_CHECK_FLAGS(tab, menu, flags, lines_count)) return; \ + TITLE(title) + #define SIMPLE_MENU_NOTITLE(tab, menu, lines_count) \ if (!check_simple(event,menu,tab,DIM(tab),(lines_count)-1)) return; From 525fee5acd02e86af6df2cd3a154e92232f1e90c Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Sun, 23 Feb 2014 19:14:30 +0100 Subject: [PATCH 53/89] .hex files ignored --- radio/src/.gitignore | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/radio/src/.gitignore b/radio/src/.gitignore index c58685a26..9bff2bce9 100644 --- a/radio/src/.gitignore +++ b/radio/src/.gitignore @@ -1,7 +1,6 @@ /stamp-opentx.h /opentx.elf /simu -/opentx.hex /opentx.map /simu.d /snapshot_*.png @@ -10,6 +9,7 @@ /*.o /*.bin /*.bin.* +/*.hex /*.lst /SCRIPTS /TEMPLATES From 0bbb3c6b4f972e1104c8416b8033c5b959954dd6 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Sun, 23 Feb 2014 19:57:51 +0100 Subject: [PATCH 54/89] Translation for the string added --- radio/src/gui/menu_model.cpp | 2 +- radio/src/translations.cpp | 1 + radio/src/translations.h | 1 + radio/src/translations/cz.h.txt | 1 + radio/src/translations/de.h.txt | 1 + radio/src/translations/en.h | 1 + radio/src/translations/es.h.txt | 1 + radio/src/translations/fi.h.txt | 1 + radio/src/translations/fr.h.txt | 1 + radio/src/translations/it.h.txt | 1 + radio/src/translations/pl.h.txt | 1 + radio/src/translations/pt.h.txt | 1 + radio/src/translations/se.h.txt | 1 + 13 files changed, 13 insertions(+), 1 deletion(-) diff --git a/radio/src/gui/menu_model.cpp b/radio/src/gui/menu_model.cpp index 427634daa..18614a044 100644 --- a/radio/src/gui/menu_model.cpp +++ b/radio/src/gui/menu_model.cpp @@ -4094,7 +4094,7 @@ void menuModelGVars(uint8_t event) bool first2seconds = (tmr10ms - menuEntryTime > 200); /*2 seconds*/ if (first2seconds) { - menuTitle = "GLOBAL V."; // TODO translate + menuTitle = STR_GLOBAL_V; for (int i=0; i Date: Sun, 23 Feb 2014 19:58:52 +0100 Subject: [PATCH 55/89] Script to automatically add a translation into all files. Syntax: addtr.py TR_GLOBAL_V "GLOBAL V." TR_GLOBAL_VARS --- radio/util/addtr.py | 36 ++++++++++++++++++++++++++++++++++++ 1 file changed, 36 insertions(+) create mode 100644 radio/util/addtr.py diff --git a/radio/util/addtr.py b/radio/util/addtr.py new file mode 100644 index 000000000..2c4a45858 --- /dev/null +++ b/radio/util/addtr.py @@ -0,0 +1,36 @@ +#!/bin/env python + +import sys, glob + +string = sys.argv[1] +translation = sys.argv[2] +after = sys.argv[3] + +def addLine(filename, newline): + print filename, newline + lines = file(filename, 'r').readlines() + for i, line in enumerate(lines): + if after in line: + lines.insert(i+1, newline + '\n') + break + file(filename, 'w').writelines(lines) + +def modifyTranslations(): + for filename in ['translations/en.h'] + glob.glob('translations/*.h.txt'): + newline = "#define " + string + " "*(23-len(string)) + '"' + translation + '"' + addLine(filename, newline) + +def modifyDeclaration(): + newline = "extern const pm_char S" + string + "[];" + filename = "translations.h" + addLine(filename, newline) + +def modifyDefinition(): + newline = "const pm_char S" + string + "[] PROGMEM = " + string + ";" + filename = "translations.cpp" + addLine(filename, newline) + +modifyTranslations() +modifyDeclaration() +modifyDefinition() + From 3ac1a03d96c594380bf9ea04ec3b7330d1296aa7 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Mon, 24 Feb 2014 07:06:26 +0100 Subject: [PATCH 56/89] This sine wave is reported as better than the previous one --- radio/src/audio_arm.cpp | 206 ++++++++++++++++++++-------------------- radio/util/sinus.py | 2 +- 2 files changed, 104 insertions(+), 104 deletions(-) diff --git a/radio/src/audio_arm.cpp b/radio/src/audio_arm.cpp index 139b17f45..ba0c4ed94 100644 --- a/radio/src/audio_arm.cpp +++ b/radio/src/audio_arm.cpp @@ -41,109 +41,109 @@ extern OS_MutexID audioMutex; const int16_t sineValues[] = { - 0, 684, 1367, 2050, 2732, 3413, 4092, 4768, 5442, 6113, - 6782, 7446, 8107, 8763, 9415, 10062, 10704, 11340, 11970, 12595, - 13212, 13823, 14427, 15024, 15613, 16194, 16766, 17330, 17886, 18432, - 18970, 19497, 20015, 20523, 21021, 21509, 21986, 22452, 22907, 23351, - 23784, 24206, 24616, 25014, 25400, 25775, 26137, 26487, 26825, 27151, - 27464, 27765, 28053, 28329, 28592, 28843, 29081, 29306, 29519, 29719, - 29906, 30081, 30244, 30394, 30532, 30657, 30770, 30872, 30961, 31038, - 31104, 31157, 31200, 31231, 31251, 31260, 31258, 31245, 31222, 31188, - 31144, 31091, 31027, 30955, 30873, 30782, 30682, 30574, 30457, 30333, - 30200, 30061, 29914, 29760, 29599, 29432, 29259, 29080, 28895, 28706, - 28511, 28312, 28108, 27900, 27689, 27474, 27256, 27035, 26812, 26586, - 26359, 26130, 25899, 25668, 25436, 25203, 24971, 24738, 24506, 24275, - 24045, 23816, 23588, 23363, 23140, 22919, 22701, 22485, 22273, 22065, - 21860, 21659, 21462, 21269, 21081, 20898, 20719, 20546, 20378, 20216, - 20059, 19909, 19764, 19626, 19494, 19368, 19249, 19137, 19032, 18934, - 18842, 18758, 18681, 18612, 18550, 18495, 18448, 18408, 18376, 18351, - 18334, 18324, 18322, 18328, 18341, 18362, 18390, 18426, 18469, 18519, - 18577, 18641, 18713, 18792, 18878, 18970, 19070, 19176, 19288, 19406, - 19531, 19662, 19798, 19941, 20088, 20242, 20400, 20563, 20731, 20904, - 21081, 21263, 21448, 21637, 21830, 22026, 22226, 22428, 22633, 22840, - 23050, 23261, 23475, 23690, 23906, 24123, 24342, 24560, 24779, 24998, - 25217, 25436, 25654, 25871, 26087, 26302, 26515, 26726, 26935, 27142, - 27347, 27549, 27747, 27943, 28135, 28324, 28509, 28690, 28867, 29039, - 29207, 29370, 29528, 29681, 29829, 29972, 30109, 30240, 30365, 30484, - 30598, 30705, 30805, 30899, 30987, 31068, 31142, 31210, 31270, 31324, - 31370, 31410, 31442, 31467, 31485, 31496, 31500, 31496, 31485, 31467, - 31442, 31410, 31370, 31324, 31270, 31210, 31142, 31068, 30987, 30899, - 30805, 30705, 30598, 30484, 30365, 30240, 30109, 29972, 29829, 29681, - 29528, 29370, 29207, 29039, 28867, 28690, 28509, 28324, 28135, 27943, - 27747, 27549, 27347, 27142, 26935, 26726, 26515, 26302, 26087, 25871, - 25654, 25436, 25217, 24998, 24779, 24560, 24342, 24123, 23906, 23690, - 23475, 23261, 23050, 22840, 22633, 22428, 22226, 22026, 21830, 21637, - 21448, 21263, 21081, 20904, 20731, 20563, 20400, 20242, 20088, 19941, - 19798, 19662, 19531, 19406, 19288, 19176, 19070, 18970, 18878, 18792, - 18713, 18641, 18577, 18519, 18469, 18426, 18390, 18362, 18341, 18328, - 18322, 18324, 18334, 18351, 18376, 18408, 18448, 18495, 18550, 18612, - 18681, 18758, 18842, 18934, 19032, 19137, 19249, 19368, 19494, 19626, - 19764, 19909, 20059, 20216, 20378, 20546, 20719, 20898, 21081, 21269, - 21462, 21659, 21860, 22065, 22273, 22485, 22701, 22919, 23140, 23363, - 23588, 23816, 24045, 24275, 24506, 24738, 24971, 25203, 25436, 25668, - 25899, 26130, 26359, 26586, 26812, 27035, 27256, 27474, 27689, 27900, - 28108, 28312, 28511, 28706, 28895, 29080, 29259, 29432, 29599, 29760, - 29914, 30061, 30200, 30333, 30457, 30574, 30682, 30782, 30873, 30955, - 31027, 31091, 31144, 31188, 31222, 31245, 31258, 31260, 31251, 31231, - 31200, 31157, 31104, 31038, 30961, 30872, 30770, 30657, 30532, 30394, - 30244, 30081, 29906, 29719, 29519, 29306, 29081, 28843, 28592, 28329, - 28053, 27765, 27464, 27151, 26825, 26487, 26137, 25775, 25400, 25014, - 24616, 24206, 23784, 23351, 22907, 22452, 21986, 21509, 21021, 20523, - 20015, 19497, 18970, 18432, 17886, 17330, 16766, 16194, 15613, 15024, - 14427, 13823, 13212, 12595, 11970, 11340, 10704, 10062, 9415, 8763, - 8107, 7446, 6782, 6113, 5442, 4768, 4092, 3413, 2732, 2050, - 1367, 684, 0, -684, -1367, -2050, -2732, -3413, -4092, -4768, - -5442, -6113, -6782, -7446, -8107, -8763, -9415, -10062, -10704, -11340, - -11970, -12595, -13212, -13823, -14427, -15024, -15613, -16194, -16766, -17330, - -17886, -18432, -18970, -19497, -20015, -20523, -21021, -21509, -21986, -22452, - -22907, -23351, -23784, -24206, -24616, -25014, -25400, -25775, -26137, -26487, - -26825, -27151, -27464, -27765, -28053, -28329, -28592, -28843, -29081, -29306, - -29519, -29719, -29906, -30081, -30244, -30394, -30532, -30657, -30770, -30872, - -30961, -31038, -31104, -31157, -31200, -31231, -31251, -31260, -31258, -31245, - -31222, -31188, -31144, -31091, -31027, -30955, -30873, -30782, -30682, -30574, - -30457, -30333, -30200, -30061, -29914, -29760, -29599, -29432, -29259, -29080, - -28895, -28706, -28511, -28312, -28108, -27900, -27689, -27474, -27256, -27035, - -26812, -26586, -26359, -26130, -25899, -25668, -25436, -25203, -24971, -24738, - -24506, -24275, -24045, -23816, -23588, -23363, -23140, -22919, -22701, -22485, - -22273, -22065, -21860, -21659, -21462, -21269, -21081, -20898, -20719, -20546, - -20378, -20216, -20059, -19909, -19764, -19626, -19494, -19368, -19249, -19137, - -19032, -18934, -18842, -18758, -18681, -18612, -18550, -18495, -18448, -18408, - -18376, -18351, -18334, -18324, -18322, -18328, -18341, -18362, -18390, -18426, - -18469, -18519, -18577, -18641, -18713, -18792, -18878, -18970, -19070, -19176, - -19288, -19406, -19531, -19662, -19798, -19941, -20088, -20242, -20400, -20563, - -20731, -20904, -21081, -21263, -21448, -21637, -21830, -22026, -22226, -22428, - -22633, -22840, -23050, -23261, -23475, -23690, -23906, -24123, -24342, -24560, - -24779, -24998, -25217, -25436, -25654, -25871, -26087, -26302, -26515, -26726, - -26935, -27142, -27347, -27549, -27747, -27943, -28135, -28324, -28509, -28690, - -28867, -29039, -29207, -29370, -29528, -29681, -29829, -29972, -30109, -30240, - -30365, -30484, -30598, -30705, -30805, -30899, -30987, -31068, -31142, -31210, - -31270, -31324, -31370, -31410, -31442, -31467, -31485, -31496, -31500, -31496, - -31485, -31467, -31442, -31410, -31370, -31324, -31270, -31210, -31142, -31068, - -30987, -30899, -30805, -30705, -30598, -30484, -30365, -30240, -30109, -29972, - -29829, -29681, -29528, -29370, -29207, -29039, -28867, -28690, -28509, -28324, - -28135, -27943, -27747, -27549, -27347, -27142, -26935, -26726, -26515, -26302, - -26087, -25871, -25654, -25436, -25217, -24998, -24779, -24560, -24342, -24123, - -23906, -23690, -23475, -23261, -23050, -22840, -22633, -22428, -22226, -22026, - -21830, -21637, -21448, -21263, -21081, -20904, -20731, -20563, -20400, -20242, - -20088, -19941, -19798, -19662, -19531, -19406, -19288, -19176, -19070, -18970, - -18878, -18792, -18713, -18641, -18577, -18519, -18469, -18426, -18390, -18362, - -18341, -18328, -18322, -18324, -18334, -18351, -18376, -18408, -18448, -18495, - -18550, -18612, -18681, -18758, -18842, -18934, -19032, -19137, -19249, -19368, - -19494, -19626, -19764, -19909, -20059, -20216, -20378, -20546, -20719, -20898, - -21081, -21269, -21462, -21659, -21860, -22065, -22273, -22485, -22701, -22919, - -23140, -23363, -23588, -23816, -24045, -24275, -24506, -24738, -24971, -25203, - -25436, -25668, -25899, -26130, -26359, -26586, -26812, -27035, -27256, -27474, - -27689, -27900, -28108, -28312, -28511, -28706, -28895, -29080, -29259, -29432, - -29599, -29760, -29914, -30061, -30200, -30333, -30457, -30574, -30682, -30782, - -30873, -30955, -31027, -31091, -31144, -31188, -31222, -31245, -31258, -31260, - -31251, -31231, -31200, -31157, -31104, -31038, -30961, -30872, -30770, -30657, - -30532, -30394, -30244, -30081, -29906, -29719, -29519, -29306, -29081, -28843, - -28592, -28329, -28053, -27765, -27464, -27151, -26825, -26487, -26137, -25775, - -25400, -25014, -24616, -24206, -23784, -23351, -22907, -22452, -21986, -21509, - -21021, -20523, -20015, -19497, -18970, -18432, -17886, -17330, -16766, -16194, - -15613, -15024, -14427, -13823, -13212, -12595, -11970, -11340, -10704, -10062, - -9415, -8763, -8107, -7446, -6782, -6113, -5442, -4768, -4092, -3413, - -2732, -2050, -1367, -684, + 0, 196, 392, 588, 784, 980, 1175, 1370, 1564, 1758, + 1951, 2143, 2335, 2525, 2715, 2904, 3091, 3278, 3463, 3647, + 3829, 4011, 4190, 4369, 4545, 4720, 4894, 5065, 5235, 5403, + 5569, 5733, 5895, 6055, 6213, 6369, 6522, 6673, 6822, 6969, + 7113, 7255, 7395, 7532, 7667, 7799, 7929, 8056, 8180, 8302, + 8422, 8539, 8653, 8765, 8874, 8980, 9084, 9185, 9283, 9379, + 9472, 9562, 9650, 9735, 9818, 9898, 9975, 10050, 10123, 10192, + 10260, 10324, 10387, 10447, 10504, 10559, 10612, 10663, 10711, 10757, + 10801, 10843, 10882, 10920, 10955, 10989, 11020, 11050, 11078, 11104, + 11128, 11151, 11172, 11191, 11209, 11225, 11240, 11254, 11266, 11277, + 11287, 11296, 11303, 11310, 11316, 11320, 11324, 11327, 11330, 11331, + 11332, 11333, 11333, 11333, 11332, 11331, 11329, 11328, 11326, 11324, + 11323, 11321, 11319, 11318, 11316, 11315, 11314, 11313, 11313, 11313, + 11314, 11315, 11317, 11319, 11323, 11326, 11331, 11336, 11342, 11349, + 11356, 11365, 11375, 11385, 11397, 11409, 11423, 11437, 11453, 11470, + 11488, 11507, 11527, 11548, 11571, 11595, 11620, 11646, 11673, 11702, + 11732, 11763, 11795, 11828, 11863, 11899, 11936, 11974, 12013, 12054, + 12095, 12138, 12182, 12227, 12273, 12320, 12368, 12417, 12467, 12518, + 12570, 12623, 12676, 12731, 12786, 12842, 12898, 12956, 13014, 13072, + 13131, 13191, 13251, 13311, 13372, 13433, 13495, 13556, 13618, 13680, + 13743, 13805, 13867, 13929, 13991, 14053, 14115, 14177, 14238, 14299, + 14359, 14419, 14479, 14538, 14597, 14655, 14712, 14768, 14824, 14879, + 14933, 14986, 15039, 15090, 15140, 15189, 15237, 15284, 15330, 15375, + 15418, 15460, 15500, 15539, 15577, 15614, 15648, 15682, 15714, 15744, + 15772, 15799, 15825, 15849, 15871, 15891, 15910, 15927, 15942, 15955, + 15967, 15977, 15985, 15991, 15996, 15999, 16000, 15999, 15996, 15991, + 15985, 15977, 15967, 15955, 15942, 15927, 15910, 15891, 15871, 15849, + 15825, 15799, 15772, 15744, 15714, 15682, 15648, 15614, 15577, 15539, + 15500, 15460, 15418, 15375, 15330, 15284, 15237, 15189, 15140, 15090, + 15039, 14986, 14933, 14879, 14824, 14768, 14712, 14655, 14597, 14538, + 14479, 14419, 14359, 14299, 14238, 14177, 14115, 14053, 13991, 13929, + 13867, 13805, 13743, 13680, 13618, 13556, 13495, 13433, 13372, 13311, + 13251, 13191, 13131, 13072, 13014, 12956, 12898, 12842, 12786, 12731, + 12676, 12623, 12570, 12518, 12467, 12417, 12368, 12320, 12273, 12227, + 12182, 12138, 12095, 12054, 12013, 11974, 11936, 11899, 11863, 11828, + 11795, 11763, 11732, 11702, 11673, 11646, 11620, 11595, 11571, 11548, + 11527, 11507, 11488, 11470, 11453, 11437, 11423, 11409, 11397, 11385, + 11375, 11365, 11356, 11349, 11342, 11336, 11331, 11326, 11323, 11319, + 11317, 11315, 11314, 11313, 11313, 11313, 11314, 11315, 11316, 11318, + 11319, 11321, 11323, 11324, 11326, 11328, 11329, 11331, 11332, 11333, + 11333, 11333, 11332, 11331, 11330, 11327, 11324, 11320, 11316, 11310, + 11303, 11296, 11287, 11277, 11266, 11254, 11240, 11225, 11209, 11191, + 11172, 11151, 11128, 11104, 11078, 11050, 11020, 10989, 10955, 10920, + 10882, 10843, 10801, 10757, 10711, 10663, 10612, 10559, 10504, 10447, + 10387, 10324, 10260, 10192, 10123, 10050, 9975, 9898, 9818, 9735, + 9650, 9562, 9472, 9379, 9283, 9185, 9084, 8980, 8874, 8765, + 8653, 8539, 8422, 8302, 8180, 8056, 7929, 7799, 7667, 7532, + 7395, 7255, 7113, 6969, 6822, 6673, 6522, 6369, 6213, 6055, + 5895, 5733, 5569, 5403, 5235, 5065, 4894, 4720, 4545, 4369, + 4190, 4011, 3829, 3647, 3463, 3278, 3091, 2904, 2715, 2525, + 2335, 2143, 1951, 1758, 1564, 1370, 1175, 980, 784, 588, + 392, 196, 0, -196, -392, -588, -784, -980, -1175, -1370, + -1564, -1758, -1951, -2143, -2335, -2525, -2715, -2904, -3091, -3278, + -3463, -3647, -3829, -4011, -4190, -4369, -4545, -4720, -4894, -5065, + -5235, -5403, -5569, -5733, -5895, -6055, -6213, -6369, -6522, -6673, + -6822, -6969, -7113, -7255, -7395, -7532, -7667, -7799, -7929, -8056, + -8180, -8302, -8422, -8539, -8653, -8765, -8874, -8980, -9084, -9185, + -9283, -9379, -9472, -9562, -9650, -9735, -9818, -9898, -9975, -10050, + -10123, -10192, -10260, -10324, -10387, -10447, -10504, -10559, -10612, -10663, + -10711, -10757, -10801, -10843, -10882, -10920, -10955, -10989, -11020, -11050, + -11078, -11104, -11128, -11151, -11172, -11191, -11209, -11225, -11240, -11254, + -11266, -11277, -11287, -11296, -11303, -11310, -11316, -11320, -11324, -11327, + -11330, -11331, -11332, -11333, -11333, -11333, -11332, -11331, -11329, -11328, + -11326, -11324, -11323, -11321, -11319, -11318, -11316, -11315, -11314, -11313, + -11313, -11313, -11314, -11315, -11317, -11319, -11323, -11326, -11331, -11336, + -11342, -11349, -11356, -11365, -11375, -11385, -11397, -11409, -11423, -11437, + -11453, -11470, -11488, -11507, -11527, -11548, -11571, -11595, -11620, -11646, + -11673, -11702, -11732, -11763, -11795, -11828, -11863, -11899, -11936, -11974, + -12013, -12054, -12095, -12138, -12182, -12227, -12273, -12320, -12368, -12417, + -12467, -12518, -12570, -12623, -12676, -12731, -12786, -12842, -12898, -12956, + -13014, -13072, -13131, -13191, -13251, -13311, -13372, -13433, -13495, -13556, + -13618, -13680, -13743, -13805, -13867, -13929, -13991, -14053, -14115, -14177, + -14238, -14299, -14359, -14419, -14479, -14538, -14597, -14655, -14712, -14768, + -14824, -14879, -14933, -14986, -15039, -15090, -15140, -15189, -15237, -15284, + -15330, -15375, -15418, -15460, -15500, -15539, -15577, -15614, -15648, -15682, + -15714, -15744, -15772, -15799, -15825, -15849, -15871, -15891, -15910, -15927, + -15942, -15955, -15967, -15977, -15985, -15991, -15996, -15999, -16000, -15999, + -15996, -15991, -15985, -15977, -15967, -15955, -15942, -15927, -15910, -15891, + -15871, -15849, -15825, -15799, -15772, -15744, -15714, -15682, -15648, -15614, + -15577, -15539, -15500, -15460, -15418, -15375, -15330, -15284, -15237, -15189, + -15140, -15090, -15039, -14986, -14933, -14879, -14824, -14768, -14712, -14655, + -14597, -14538, -14479, -14419, -14359, -14299, -14238, -14177, -14115, -14053, + -13991, -13929, -13867, -13805, -13743, -13680, -13618, -13556, -13495, -13433, + -13372, -13311, -13251, -13191, -13131, -13072, -13014, -12956, -12898, -12842, + -12786, -12731, -12676, -12623, -12570, -12518, -12467, -12417, -12368, -12320, + -12273, -12227, -12182, -12138, -12095, -12054, -12013, -11974, -11936, -11899, + -11863, -11828, -11795, -11763, -11732, -11702, -11673, -11646, -11620, -11595, + -11571, -11548, -11527, -11507, -11488, -11470, -11453, -11437, -11423, -11409, + -11397, -11385, -11375, -11365, -11356, -11349, -11342, -11336, -11331, -11326, + -11323, -11319, -11317, -11315, -11314, -11313, -11313, -11313, -11314, -11315, + -11316, -11318, -11319, -11321, -11323, -11324, -11326, -11328, -11329, -11331, + -11332, -11333, -11333, -11333, -11332, -11331, -11330, -11327, -11324, -11320, + -11316, -11310, -11303, -11296, -11287, -11277, -11266, -11254, -11240, -11225, + -11209, -11191, -11172, -11151, -11128, -11104, -11078, -11050, -11020, -10989, + -10955, -10920, -10882, -10843, -10801, -10757, -10711, -10663, -10612, -10559, + -10504, -10447, -10387, -10324, -10260, -10192, -10123, -10050, -9975, -9898, + -9818, -9735, -9650, -9562, -9472, -9379, -9283, -9185, -9084, -8980, + -8874, -8765, -8653, -8539, -8422, -8302, -8180, -8056, -7929, -7799, + -7667, -7532, -7395, -7255, -7113, -6969, -6822, -6673, -6522, -6369, + -6213, -6055, -5895, -5733, -5569, -5403, -5235, -5065, -4894, -4720, + -4545, -4369, -4190, -4011, -3829, -3647, -3463, -3278, -3091, -2904, + -2715, -2525, -2335, -2143, -1951, -1758, -1564, -1370, -1175, -980, + -784, -588, -392, -196, }; #if defined(SDCARD) diff --git a/radio/util/sinus.py b/radio/util/sinus.py index 0754c4447..727090e49 100644 --- a/radio/util/sinus.py +++ b/radio/util/sinus.py @@ -3,7 +3,7 @@ import math samples = 1024 -amplitudes = (63000, 0, 20000, 0, 20000) +amplitudes = (32000, 0, 4000, 0, 4000) max = 0 min = 0 From 2a8abd08da6a09468a471f1e14a61bd780206801 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Mon, 24 Feb 2014 07:30:59 +0100 Subject: [PATCH 57/89] Issue #741 fixed - a==x added in logical switches functions --- companion/src/eeprominterface.cpp | 2 ++ companion/src/eeprominterface.h | 1 + companion/src/firmwares/opentx/opentxeeprom.cpp | 4 +++- companion/src/helpers.cpp | 1 + companion/src/modeledit/customswitches.cpp | 8 ++++---- radio/src/eeprom_conversions.cpp | 1 + radio/src/myeeprom.h | 3 +++ radio/src/opentx.cpp | 5 +++++ radio/src/translations/cz.h.txt | 8 +++++++- radio/src/translations/de.h.txt | 8 +++++++- radio/src/translations/en.h | 8 +++++++- radio/src/translations/es.h.txt | 8 +++++++- radio/src/translations/fi.h.txt | 8 +++++++- radio/src/translations/fr.h.txt | 8 +++++++- radio/src/translations/it.h.txt | 8 +++++++- radio/src/translations/pl.h.txt | 8 +++++++- radio/src/translations/pt.h.txt | 8 +++++++- radio/src/translations/se.h.txt | 8 +++++++- 18 files changed, 90 insertions(+), 15 deletions(-) diff --git a/companion/src/eeprominterface.cpp b/companion/src/eeprominterface.cpp index 1df1f4e98..749a54d70 100644 --- a/companion/src/eeprominterface.cpp +++ b/companion/src/eeprominterface.cpp @@ -428,6 +428,8 @@ QString LogicalSwitchData::funcToString() case LS_FN_DAPOS: return QObject::tr("|d|>=x"); case LS_FN_VEQUAL: + return QObject::tr("a=x"); + case LS_FN_VALMOSTEQUAL: return QObject::tr("a~x"); case LS_FN_TIMER: return QObject::tr("Timer"); diff --git a/companion/src/eeprominterface.h b/companion/src/eeprominterface.h index 07919466c..316c263dc 100644 --- a/companion/src/eeprominterface.h +++ b/companion/src/eeprominterface.h @@ -597,6 +597,7 @@ enum CSFunction { LS_FN_DPOS, LS_FN_DAPOS, LS_FN_VEQUAL, // added at the end to avoid everything renumbered + LS_FN_VALMOSTEQUAL, LS_FN_TIMER, LS_FN_STICKY, LS_FN_STAY, diff --git a/companion/src/firmwares/opentx/opentxeeprom.cpp b/companion/src/firmwares/opentx/opentxeeprom.cpp index 37f148900..01d9cab65 100644 --- a/companion/src/firmwares/opentx/opentxeeprom.cpp +++ b/companion/src/firmwares/opentx/opentxeeprom.cpp @@ -1063,8 +1063,10 @@ class LogicalSwitchesFunctionsTable: public ConversionTable { int val=0; bool afterrelease21March2013 = IS_AFTER_RELEASE_21_MARCH_2013(board, version); addConversion(LS_FN_OFF, val++); - if (afterrelease21March2013) + if (IS_ARM(board) && version >= 216) addConversion(LS_FN_VEQUAL, val++); + if (afterrelease21March2013) + addConversion(LS_FN_VALMOSTEQUAL, val++); addConversion(LS_FN_VPOS, val++); addConversion(LS_FN_VNEG, val++); if (IS_ARM(board) && version >= 216) val++; // later RANGE diff --git a/companion/src/helpers.cpp b/companion/src/helpers.cpp index 2c7f9fc0c..e0cd7b91c 100644 --- a/companion/src/helpers.cpp +++ b/companion/src/helpers.cpp @@ -643,6 +643,7 @@ void populateCSWCB(QComboBox *b, int value) int order[] = { LS_FN_OFF, LS_FN_VEQUAL, // added at the end to avoid everything renumbered + LS_FN_VALMOSTEQUAL, // added at the end to avoid everything renumbered LS_FN_VPOS, LS_FN_VNEG, // LS_FN_RANGE, diff --git a/companion/src/modeledit/customswitches.cpp b/companion/src/modeledit/customswitches.cpp index cf02f4430..d86a1a487 100644 --- a/companion/src/modeledit/customswitches.cpp +++ b/companion/src/modeledit/customswitches.cpp @@ -121,7 +121,7 @@ void LogicalSwitchesPanel::v1Edited(int value) if (model.customSw[i].getFunctionFamily() == LS_FAMILY_VOFS) { RawSource source = RawSource(model.customSw[i].val1, &model); if (source.type == SOURCE_TYPE_TELEMETRY) { - if (model.customSw[i].func > LS_FN_ELESS && model.customSw[i].func < LS_FN_VEQUAL) { + if (model.customSw[i].func == LS_FN_DPOS || model.customSw[i].func == LS_FN_DAPOS) { model.customSw[i].val2 = 0; } else { @@ -130,7 +130,7 @@ void LogicalSwitchesPanel::v1Edited(int value) } else { RawSourceRange range = source.getRange(); - if (model.customSw[i].func > LS_FN_ELESS && model.customSw[i].func < LS_FN_VEQUAL) { + if (model.customSw[i].func == LS_FN_DPOS || model.customSw[i].func == LS_FN_DAPOS) { model.customSw[i].val2 = (cswitchOffset[i]->value() / range.step); } else { @@ -208,7 +208,7 @@ void LogicalSwitchesPanel::edited() { source = RawSource(model.customSw[i].val1, &model); RawSourceRange range = source.getRange(); - if (model.customSw[i].func>LS_FN_ELESS && model.customSw[i].funcvalue() / range.step); cswitchOffset[i]->setValue(model.customSw[i].val2*range.step); } @@ -269,7 +269,7 @@ void LogicalSwitchesPanel::setSwitchWidgetVisibility(int i) populateSourceCB(cswitchSource1[i], source, model, POPULATE_SOURCES | POPULATE_VIRTUAL_INPUTS | POPULATE_TRIMS | POPULATE_SWITCHES | POPULATE_TELEMETRY | (GetEepromInterface()->getCapability(GvarsInCS) ? POPULATE_GVARS : 0)); cswitchOffset[i]->setDecimals(range.decimals); cswitchOffset[i]->setSingleStep(range.step); - if (model.customSw[i].func>LS_FN_ELESS && model.customSw[i].funcsetMinimum(range.step*-127); cswitchOffset[i]->setMaximum(range.step*127); cswitchOffset[i]->setValue(range.step*model.customSw[i].val2); diff --git a/radio/src/eeprom_conversions.cpp b/radio/src/eeprom_conversions.cpp index f12353cb0..dc3707352 100644 --- a/radio/src/eeprom_conversions.cpp +++ b/radio/src/eeprom_conversions.cpp @@ -466,6 +466,7 @@ void ConvertModel_215_to_216(ModelData &model) for (uint8_t i=0; i<32; i++) { LogicalSwitchData & sw = g_model.customSw[i]; sw.func = oldModel.customSw[i].func; + if (sw.func >= LS_FUNC_VEQUAL) sw.func += 1; if (sw.func >= LS_FUNC_RANGE) sw.func += 1; if (sw.func >= LS_FUNC_STAY) sw.func += 1; sw.v1 = oldModel.customSw[i].v1; diff --git a/radio/src/myeeprom.h b/radio/src/myeeprom.h index 94b6cbb9e..2527383a2 100644 --- a/radio/src/myeeprom.h +++ b/radio/src/myeeprom.h @@ -686,7 +686,10 @@ PACK( union u_int8int16_t { enum LogicalSwitchesFunctions { LS_FUNC_NONE, +#if defined(CPUARM) LS_FUNC_VEQUAL, // v==offset +#endif + LS_FUNC_VALMOSTEQUAL, // v~=offset LS_FUNC_VPOS, // v>offset LS_FUNC_VNEG, // vfunc) { +#if defined(CPUARM) case LS_FUNC_VEQUAL: + result = (x==y); + break; +#endif + case LS_FUNC_VALMOSTEQUAL: #if defined(GVARS) if (v1 >= MIXSRC_GVAR1 && v1 <= MIXSRC_LAST_GVAR) result = (x==y); diff --git a/radio/src/translations/cz.h.txt b/radio/src/translations/cz.h.txt index 1fa49ad61..e69af0f29 100644 --- a/radio/src/translations/cz.h.txt +++ b/radio/src/translations/cz.h.txt @@ -167,8 +167,14 @@ #endif #endif +#if defined(CPUARM) + #define TR_CSWEQUAL "a=x\0 " +#else + #define TR_CSWEQUAL +#endif + #define LEN_VCSWFUNC "\005" -#define TR_VCSWFUNC "---\0 ""a{x\0 ""a>x\0 ""ax""|a|b\0 ""ax\0 ""ax""|a|b\0 ""ax\0 ""ax""|a|b\0 ""ax\0 ""ax""|a|b\0 ""ax\0 ""ax""|a|b\0 ""ax\0 ""ax""|a|b\0 ""ax\0 ""ax""|a|b\0 ""ax\0 ""ax""|a|b\0 ""ax\0 ""ax""|a|b\0 ""ax\0 ""ax""|a|b\0 ""ax\0 ""ax""|a|b\0 ""ax\0 ""ax""|a|b\0 ""ax\0 ""ax""|a|b\0 ""ax\0 ""ax""|a|b\0 ""ax\0 ""ax""|a|b\0 ""ax\0 ""ax""|a|b\0 ""ax\0 ""ax""|a|b\0 ""ax\0 ""ax""|a|b\0 ""ax\0 ""ax""|a|b\0 ""ax\0 ""ax""|a|b\0 ""a Date: Mon, 24 Feb 2014 07:45:37 +0100 Subject: [PATCH 58/89] Issue #650 fixed - 0.1s precision in durations/delays for logical switches --- companion/src/eeprominterface.cpp | 4 ++-- companion/src/modeledit/customswitches.cpp | 16 ++++++++-------- radio/src/eeprom_conversions.cpp | 4 ++-- radio/src/gui/menu_model.cpp | 4 ++-- radio/src/myeeprom.h | 4 ++-- radio/src/opentx.cpp | 4 ++-- 6 files changed, 18 insertions(+), 18 deletions(-) diff --git a/companion/src/eeprominterface.cpp b/companion/src/eeprominterface.cpp index 1df1f4e98..d97b8cf1a 100644 --- a/companion/src/eeprominterface.cpp +++ b/companion/src/eeprominterface.cpp @@ -539,9 +539,9 @@ QString LogicalSwitchData::toString(const ModelData & model) if (GetEepromInterface()->getCapability(LogicalSwitchesExt)) { if (delay) - result += QObject::tr(" Delay %1 sec").arg(delay/2.0); + result += QObject::tr(" Delay %1 sec").arg(delay/10.0); if (duration) - result += QObject::tr(" Duration %1 sec").arg(duration/2.0); + result += QObject::tr(" Duration %1 sec").arg(duration/10.0); } return result; diff --git a/companion/src/modeledit/customswitches.cpp b/companion/src/modeledit/customswitches.cpp index cf02f4430..ad418df68 100644 --- a/companion/src/modeledit/customswitches.cpp +++ b/companion/src/modeledit/customswitches.cpp @@ -85,8 +85,8 @@ LogicalSwitchesPanel::LogicalSwitchesPanel(QWidget * parent, ModelData & model): // Duration cswitchDuration[i] = new QDoubleSpinBox(this); cswitchDuration[i]->setProperty("index", i); - cswitchDuration[i]->setSingleStep(0.5); - cswitchDuration[i]->setMaximum(50); + cswitchDuration[i]->setSingleStep(0.1); + cswitchDuration[i]->setMaximum(25); cswitchDuration[i]->setMinimum(0); cswitchDuration[i]->setAccelerated(true); cswitchDuration[i]->setDecimals(1); @@ -96,8 +96,8 @@ LogicalSwitchesPanel::LogicalSwitchesPanel(QWidget * parent, ModelData & model): // Delay cswitchDelay[i] = new QDoubleSpinBox(this); cswitchDelay[i]->setProperty("index", i); - cswitchDelay[i]->setSingleStep(0.5); - cswitchDelay[i]->setMaximum(50); + cswitchDelay[i]->setSingleStep(0.1); + cswitchDelay[i]->setMaximum(25); cswitchDelay[i]->setMinimum(0); cswitchDelay[i]->setAccelerated(true); cswitchDelay[i]->setDecimals(1); @@ -164,14 +164,14 @@ void LogicalSwitchesPanel::andEdited(int value) void LogicalSwitchesPanel::durationEdited(double duration) { int index = sender()->property("index").toInt(); - model.customSw[index].duration = (uint8_t)round(duration*2); + model.customSw[index].duration = (uint8_t)round(duration*10); emit modified(); } void LogicalSwitchesPanel::delayEdited(double delay) { int index = sender()->property("index").toInt(); - model.customSw[index].delay = (uint8_t)round(delay*2); + model.customSw[index].delay = (uint8_t)round(delay*10); emit modified(); } @@ -325,8 +325,8 @@ void LogicalSwitchesPanel::update() lock = true; populateAndSwitchCB(cswitchAnd[i], RawSwitch(model.customSw[i].andsw)); if (GetEepromInterface()->getCapability(LogicalSwitchesExt)) { - cswitchDuration[i]->setValue(model.customSw[i].duration/2.0); - cswitchDelay[i]->setValue(model.customSw[i].delay/2.0); + cswitchDuration[i]->setValue(model.customSw[i].duration/10.0); + cswitchDelay[i]->setValue(model.customSw[i].delay/10.0); } lock = false; } diff --git a/radio/src/eeprom_conversions.cpp b/radio/src/eeprom_conversions.cpp index f12353cb0..15abd195e 100644 --- a/radio/src/eeprom_conversions.cpp +++ b/radio/src/eeprom_conversions.cpp @@ -470,8 +470,8 @@ void ConvertModel_215_to_216(ModelData &model) if (sw.func >= LS_FUNC_STAY) sw.func += 1; sw.v1 = oldModel.customSw[i].v1; sw.v2 = oldModel.customSw[i].v2; - sw.delay = oldModel.customSw[i].delay; - sw.duration = oldModel.customSw[i].duration; + sw.delay = oldModel.customSw[i].delay * 5; + sw.duration = oldModel.customSw[i].duration * 5; sw.andsw = ConvertSwitch_215_to_216(oldModel.customSw[i].andsw); #if defined(PCBTARANIS) uint8_t cstate = cswFamily(sw.func); diff --git a/radio/src/gui/menu_model.cpp b/radio/src/gui/menu_model.cpp index d1dd68a46..bb78da5ff 100644 --- a/radio/src/gui/menu_model.cpp +++ b/radio/src/gui/menu_model.cpp @@ -4363,7 +4363,7 @@ void menuModelLogicalSwitchOne(uint8_t event) case LS_FIELD_DURATION: lcd_putsLeft(y, STR_DURATION); if (cs->duration > 0) - lcd_outdezAtt(CSWONE_2ND_COLUMN, y, 5*cs->duration, attr|PREC1|LEFT); + lcd_outdezAtt(CSWONE_2ND_COLUMN, y, cs->duration, attr|PREC1|LEFT); else lcd_putsiAtt(CSWONE_2ND_COLUMN, y, STR_MMMINV, 0, attr); if (attr) CHECK_INCDEC_MODELVAR_ZERO(event, cs->duration, MAX_LS_DURATION); @@ -4371,7 +4371,7 @@ void menuModelLogicalSwitchOne(uint8_t event) case LS_FIELD_DELAY: lcd_putsLeft(y, STR_DELAY); if (cs->delay > 0) - lcd_outdezAtt(CSWONE_2ND_COLUMN, y, 5*cs->delay, attr|PREC1|LEFT); + lcd_outdezAtt(CSWONE_2ND_COLUMN, y, cs->delay, attr|PREC1|LEFT); else lcd_putsiAtt(CSWONE_2ND_COLUMN, y, STR_MMMINV, 0, attr); if (attr) CHECK_INCDEC_MODELVAR_ZERO(event, cs->delay, MAX_LS_DELAY); diff --git a/radio/src/myeeprom.h b/radio/src/myeeprom.h index 94b6cbb9e..dc427485a 100644 --- a/radio/src/myeeprom.h +++ b/radio/src/myeeprom.h @@ -712,8 +712,8 @@ enum LogicalSwitchesFunctions { }; #if defined(CPUARM) -#define MAX_LS_DURATION 120 /*60s*/ -#define MAX_LS_DELAY 120 /*60s*/ +#define MAX_LS_DURATION 250 /*25s*/ +#define MAX_LS_DELAY 250 /*25s*/ #define MAX_LS_ANDSW SWSRC_LAST typedef int16_t ls_telemetry_value_t; PACK(typedef struct t_LogicalSwitchData { // Custom Switches data diff --git a/radio/src/opentx.cpp b/radio/src/opentx.cpp index 36d95d213..75e41dd80 100644 --- a/radio/src/opentx.cpp +++ b/radio/src/opentx.cpp @@ -1589,13 +1589,13 @@ bool getSwitch(int8_t swtch) result = false; } else { - cswDelays[cs_idx] = get_tmr10ms() + (cs->delay*50); + cswDelays[cs_idx] = get_tmr10ms() + (cs->delay*10); } } if (cs->duration) { if (result && !cswStates[cs_idx]) { - cswDurations[cs_idx] = get_tmr10ms() + (cs->duration*50); + cswDurations[cs_idx] = get_tmr10ms() + (cs->duration*10); } cswStates[cs_idx] = result; From dc37677cc6a733dbaf591b108e03c8377380ee0d Mon Sep 17 00:00:00 2001 From: Kjell Kernen Date: Mon, 24 Feb 2014 12:22:46 +0100 Subject: [PATCH 59/89] Removing ER9x and Open9x specific imagery --- companion/src/images/library/00001.png | Bin 662 -> 353 bytes companion/src/images/library/00002.png | Bin 554 -> 2331 bytes companion/src/images/library/00004.png | Bin 831 -> 0 bytes companion/src/images/library/00017.png | Bin 0 -> 634 bytes .../images/library/{10001.png => 00501.png} | Bin .../images/library/{10002.png => 00502.png} | Bin companion/src/images/library/00503.png | Bin 0 -> 445 bytes companion/src/images/library/00504.png | Bin 0 -> 668 bytes companion/src/images/library/00505.png | Bin 0 -> 739 bytes companion/src/images/library/00506.png | Bin 0 -> 776 bytes companion/src/images/library/00508.png | Bin 0 -> 767 bytes companion/src/images/library/00601.png | Bin 0 -> 590 bytes companion/src/images/library/00602.png | Bin 0 -> 563 bytes companion/src/images/library/00603.png | Bin 0 -> 612 bytes companion/src/images/library/01001.png | Bin 911 -> 0 bytes companion/src/images/library/01002.png | Bin 855 -> 0 bytes companion/src/images/library/01003.png | Bin 840 -> 0 bytes companion/src/images/library/01004.png | Bin 883 -> 0 bytes companion/src/images/library/01005.png | Bin 883 -> 0 bytes companion/src/images/library/01006.png | Bin 840 -> 0 bytes companion/src/images/library/01007.png | Bin 855 -> 0 bytes companion/src/images/library/01008.png | Bin 911 -> 0 bytes companion/src/images/library/10003.png | Bin 857 -> 0 bytes companion/src/images/library/10004.png | Bin 752 -> 0 bytes companion/src/images/library/10005.png | Bin 889 -> 0 bytes companion/src/images/library/10006.png | Bin 677 -> 0 bytes companion/src/images/library/10008.png | Bin 606 -> 0 bytes companion/src/images/library/10009.png | Bin 653 -> 0 bytes companion/src/images/library/10010.png | Bin 645 -> 0 bytes companion/src/images/library/10012.png | Bin 664 -> 0 bytes companion/src/images/library/10013.png | Bin 612 -> 0 bytes companion/src/images/library/10014.png | Bin 656 -> 0 bytes companion/src/images/library/10016.png | Bin 601 -> 0 bytes companion/src/images/library/10017.png | Bin 659 -> 0 bytes companion/src/images/library/10018.png | Bin 712 -> 0 bytes companion/src/images/library/10019.png | Bin 752 -> 0 bytes companion/src/images/library/10020.png | Bin 783 -> 0 bytes companion/src/images/library/10021.png | Bin 744 -> 0 bytes companion/src/images/library/10022.png | Bin 812 -> 0 bytes companion/src/images/library/10023.png | Bin 451 -> 0 bytes companion/src/images/library/10024.png | Bin 555 -> 0 bytes companion/src/images/library/10025.png | Bin 601 -> 0 bytes companion/src/images/library/10026.png | Bin 732 -> 725 bytes companion/src/images/library/10027.png | Bin 799 -> 881 bytes companion/src/images/library/10028.png | Bin 748 -> 0 bytes companion/src/images/library/10029.png | Bin 755 -> 0 bytes companion/src/images/library/10030.png | Bin 746 -> 771 bytes companion/src/images/library/10031.png | Bin 675 -> 624 bytes companion/src/images/library/10032.png | Bin 600 -> 0 bytes companion/src/images/library/10033.png | Bin 709 -> 0 bytes companion/src/images/library/10034.png | Bin 690 -> 0 bytes companion/src/images/library/10035.png | Bin 721 -> 0 bytes companion/src/images/library/10036.png | Bin 716 -> 682 bytes companion/src/images/library/10037.png | Bin 715 -> 0 bytes companion/src/images/library/10038.png | Bin 764 -> 577 bytes companion/src/images/library/10039.png | Bin 724 -> 887 bytes companion/src/images/library/10040.png | Bin 450 -> 0 bytes companion/src/images/library/10041.png | Bin 819 -> 0 bytes companion/src/images/library/10042.png | Bin 695 -> 0 bytes companion/src/images/library/10043.png | Bin 638 -> 0 bytes companion/src/images/library/10044.png | Bin 602 -> 0 bytes companion/src/images/library/10045.png | Bin 762 -> 0 bytes companion/src/images/library/10046.png | Bin 666 -> 0 bytes companion/src/images/library/10047.png | Bin 650 -> 0 bytes companion/src/images/library/10048.png | Bin 594 -> 0 bytes companion/src/images/library/10049.png | Bin 706 -> 0 bytes companion/src/images/library/10050.png | Bin 701 -> 0 bytes companion/src/images/library/10051.png | Bin 678 -> 0 bytes companion/src/images/library/10052.png | Bin 690 -> 0 bytes companion/src/images/library/10053.png | Bin 529 -> 0 bytes companion/src/images/library/10054.png | Bin 548 -> 0 bytes companion/src/images/library/10055.png | Bin 659 -> 0 bytes companion/src/images/library/10056.png | Bin 563 -> 0 bytes companion/src/images/library/10057.png | Bin 855 -> 0 bytes companion/src/images/library/10059.png | Bin 703 -> 0 bytes companion/src/images/library/10060.png | Bin 1567 -> 0 bytes companion/src/images/library/10061.png | Bin 732 -> 0 bytes companion/src/images/library/10062.png | Bin 647 -> 0 bytes companion/src/images/library/10063.png | Bin 543 -> 0 bytes companion/src/images/library/10064.png | Bin 641 -> 0 bytes companion/src/images/library/10065.png | Bin 587 -> 0 bytes companion/src/images/library/10066.png | Bin 658 -> 0 bytes companion/src/images/library/10067.png | Bin 524 -> 0 bytes companion/src/images/library/10068.png | Bin 560 -> 0 bytes companion/src/images/library/10069.png | Bin 746 -> 0 bytes companion/src/images/library/10071.png | Bin 695 -> 0 bytes companion/src/images/library/10072.png | Bin 705 -> 0 bytes companion/src/images/library/10073.png | Bin 734 -> 0 bytes companion/src/images/library/10074.png | Bin 762 -> 0 bytes companion/src/images/library/10075.png | Bin 651 -> 0 bytes companion/src/images/library/10076.png | Bin 704 -> 0 bytes companion/src/images/library/10077.png | Bin 479 -> 0 bytes companion/src/images/library/10078.png | Bin 654 -> 0 bytes companion/src/images/library/10079.png | Bin 594 -> 0 bytes companion/src/images/library/10080.png | Bin 657 -> 0 bytes companion/src/images/library/10081.png | Bin 521 -> 0 bytes companion/src/images/library/10082.png | Bin 949 -> 0 bytes companion/src/images/library/10083.png | Bin 576 -> 529 bytes companion/src/images/library/10084.png | Bin 755 -> 0 bytes companion/src/images/library/10085.png | Bin 568 -> 573 bytes companion/src/images/library/10086.png | Bin 713 -> 0 bytes companion/src/images/library/10087.png | Bin 611 -> 0 bytes companion/src/images/library/10088.png | Bin 438 -> 466 bytes companion/src/images/library/10089.png | Bin 573 -> 0 bytes companion/src/images/library/10090.png | Bin 580 -> 607 bytes companion/src/images/library/10091.png | Bin 825 -> 0 bytes companion/src/images/library/10093.png | Bin 618 -> 529 bytes companion/src/images/library/10095.png | Bin 892 -> 0 bytes companion/src/images/library/10097.png | Bin 953 -> 0 bytes companion/src/images/library/10098.png | Bin 808 -> 863 bytes companion/src/images/library/10099.png | Bin 584 -> 0 bytes companion/src/images/library/10100.png | Bin 806 -> 0 bytes companion/src/images/library/10101.png | Bin 888 -> 0 bytes companion/src/images/library/10102.png | Bin 941 -> 0 bytes companion/src/images/library/10103.png | Bin 737 -> 0 bytes companion/src/images/library/10104.png | Bin 670 -> 572 bytes companion/src/images/library/20001.png | Bin 751 -> 469 bytes companion/src/images/library/20002.png | Bin 945 -> 609 bytes companion/src/images/library/20003.png | Bin 882 -> 492 bytes companion/src/images/library/20004.png | Bin 878 -> 712 bytes companion/src/images/library/30001.png | Bin 2879 -> 865 bytes companion/src/images/library/300011.png | Bin 0 -> 2821 bytes companion/src/images/library/30002.png | Bin 2767 -> 3381 bytes companion/src/images/library/30003.png | Bin 4233 -> 0 bytes companion/src/images/library/30004.png | Bin 3049 -> 0 bytes companion/src/images/library/30005.png | Bin 3152 -> 2395 bytes companion/src/images/library/30006.png | Bin 3600 -> 0 bytes 127 files changed, 0 insertions(+), 0 deletions(-) delete mode 100644 companion/src/images/library/00004.png create mode 100644 companion/src/images/library/00017.png rename companion/src/images/library/{10001.png => 00501.png} (100%) rename companion/src/images/library/{10002.png => 00502.png} (100%) create mode 100644 companion/src/images/library/00503.png create mode 100644 companion/src/images/library/00504.png create mode 100644 companion/src/images/library/00505.png create mode 100644 companion/src/images/library/00506.png create mode 100644 companion/src/images/library/00508.png create mode 100644 companion/src/images/library/00601.png create mode 100644 companion/src/images/library/00602.png create mode 100644 companion/src/images/library/00603.png delete mode 100644 companion/src/images/library/01001.png delete mode 100644 companion/src/images/library/01002.png delete mode 100644 companion/src/images/library/01003.png delete mode 100644 companion/src/images/library/01004.png delete mode 100644 companion/src/images/library/01005.png delete mode 100644 companion/src/images/library/01006.png delete mode 100644 companion/src/images/library/01007.png delete mode 100644 companion/src/images/library/01008.png delete mode 100644 companion/src/images/library/10003.png delete mode 100644 companion/src/images/library/10004.png delete mode 100644 companion/src/images/library/10005.png delete mode 100644 companion/src/images/library/10006.png delete mode 100644 companion/src/images/library/10008.png delete mode 100644 companion/src/images/library/10009.png delete mode 100644 companion/src/images/library/10010.png delete mode 100644 companion/src/images/library/10012.png delete mode 100644 companion/src/images/library/10013.png delete mode 100644 companion/src/images/library/10014.png delete mode 100644 companion/src/images/library/10016.png delete mode 100644 companion/src/images/library/10017.png delete mode 100644 companion/src/images/library/10018.png delete mode 100644 companion/src/images/library/10019.png delete mode 100644 companion/src/images/library/10020.png delete mode 100644 companion/src/images/library/10021.png delete mode 100644 companion/src/images/library/10022.png delete mode 100644 companion/src/images/library/10023.png delete mode 100644 companion/src/images/library/10024.png delete mode 100644 companion/src/images/library/10025.png delete mode 100644 companion/src/images/library/10028.png delete mode 100644 companion/src/images/library/10029.png delete mode 100644 companion/src/images/library/10032.png delete mode 100644 companion/src/images/library/10033.png delete mode 100644 companion/src/images/library/10034.png delete mode 100644 companion/src/images/library/10035.png delete mode 100644 companion/src/images/library/10037.png delete mode 100644 companion/src/images/library/10040.png delete mode 100644 companion/src/images/library/10041.png delete mode 100644 companion/src/images/library/10042.png delete mode 100644 companion/src/images/library/10043.png delete mode 100644 companion/src/images/library/10044.png delete mode 100644 companion/src/images/library/10045.png delete mode 100644 companion/src/images/library/10046.png delete mode 100644 companion/src/images/library/10047.png delete mode 100644 companion/src/images/library/10048.png delete mode 100644 companion/src/images/library/10049.png delete mode 100644 companion/src/images/library/10050.png delete mode 100644 companion/src/images/library/10051.png delete mode 100644 companion/src/images/library/10052.png delete mode 100644 companion/src/images/library/10053.png delete mode 100644 companion/src/images/library/10054.png delete mode 100644 companion/src/images/library/10055.png delete mode 100644 companion/src/images/library/10056.png delete mode 100644 companion/src/images/library/10057.png delete mode 100644 companion/src/images/library/10059.png delete mode 100644 companion/src/images/library/10060.png delete mode 100644 companion/src/images/library/10061.png delete mode 100644 companion/src/images/library/10062.png delete mode 100644 companion/src/images/library/10063.png delete mode 100644 companion/src/images/library/10064.png delete mode 100644 companion/src/images/library/10065.png delete mode 100644 companion/src/images/library/10066.png delete mode 100644 companion/src/images/library/10067.png delete mode 100644 companion/src/images/library/10068.png delete mode 100644 companion/src/images/library/10069.png delete mode 100644 companion/src/images/library/10071.png delete mode 100644 companion/src/images/library/10072.png delete mode 100644 companion/src/images/library/10073.png delete mode 100644 companion/src/images/library/10074.png delete mode 100644 companion/src/images/library/10075.png delete mode 100644 companion/src/images/library/10076.png delete mode 100644 companion/src/images/library/10077.png delete mode 100644 companion/src/images/library/10078.png delete mode 100644 companion/src/images/library/10079.png delete mode 100644 companion/src/images/library/10080.png delete mode 100644 companion/src/images/library/10081.png delete mode 100644 companion/src/images/library/10082.png delete mode 100644 companion/src/images/library/10084.png delete mode 100644 companion/src/images/library/10086.png delete mode 100644 companion/src/images/library/10087.png delete mode 100644 companion/src/images/library/10089.png delete mode 100644 companion/src/images/library/10091.png delete mode 100644 companion/src/images/library/10095.png delete mode 100644 companion/src/images/library/10097.png delete mode 100644 companion/src/images/library/10099.png delete mode 100644 companion/src/images/library/10100.png delete mode 100644 companion/src/images/library/10101.png delete mode 100644 companion/src/images/library/10102.png delete mode 100644 companion/src/images/library/10103.png create mode 100644 companion/src/images/library/300011.png delete mode 100644 companion/src/images/library/30003.png delete mode 100644 companion/src/images/library/30004.png delete mode 100644 companion/src/images/library/30006.png diff --git a/companion/src/images/library/00001.png b/companion/src/images/library/00001.png index 57c8485a91191a8b265538330cb57ce77100985a..0218d0570a6be5207e3bba6c272d9f3c45af1b6d 100644 GIT binary patch delta 312 zcmV-80muH91>pja7#jft0002!80|a&000J1OjJbx00960|E1ZV-H{<4f8GKZ3NJ3m z&`X;D008buL_t(I%k9!JZo@DP1yHFPJn{zhMbz+I1q@h4hmJi$ui~6QS756Pu$uxn zW=X|G;;hLSPR4^Q@)L6IQFp5#@a8y50)#ai+(^tlI(vJ-Vd_^60+pC z;(+|oKq^+r`;ru-I_G(ge*?q5Oh8Upfntmd--Q%Lg+M!l-@*o@Fg?d8`B18YO>Qtq zel4>?e*)|BQWiTwD==U?(e9uf5<}na_;2eNpmjM7HW+j^hd4K941#3| zYkUK5X**ud`*~7;%?cIz&5|2nvQ@Ss1)Ma@C5)-3$BVtW{s3tl60+Z#oo4X>0000< KMNUMnLSTZWREL`Y delta 650 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 literal 554 zcmV+_0@eMAP)(_`g8%^e{{R4h=>PzAFaQARU;qF*m;eA5Z<1fd zMgRZ-ut`KgRCwByl0lBsKoCWrE0$~_gpJsaXp3{8WQLQ3dsvD`ngiqp zOjk@n#4t0BCtuLpT6D0t!$M*J=Y1 z0AUBfHwfoyQmoVi73=T)!F1*|rmH>x z%Y_%#Yu>Y7)7&`@xd-(|JM~8Qwl|fPjI!Z|GQH>4iX3yca?IJ10Ud>FSH<47rrLk% zi-_RT^3d}JB6(Vj)!WZLTpdF|O3O7RD3)`jaa@dkTDt!9IS90r_BIEeQI?}(S$DV^ zgp6)j?HumNdDp*ay00JM`73LHLY>A!eQS);E|Gu>1UwB&2NJQw2(1#ca6oi(8&BHp s;Nc``qSPx#22e~?MgRZ*00010!qa{L0004EOGiWihy@);00009a7bBm0017s0017s0dCNB zJ^%m!2XskIMF-pq7!f-;H3pXA0008ANklY%m+juIWx&=M; z(j2RZn?t1DdJ6R-Dd<7)U=bxAq}e7%#a=~3JT9}L$;C?|X16O1cc{4vBZ{B+Vqv9w4?~EAUL!={ycmN>bh#~0!GAe%!ncc68djBD? zxXR*F!9+kFVLAz1ml;p^Ca$50N-_%k3H!xihRK$`90s8^;TxuDG(YKj2*jOG$TwO> z(=-&$kza;&xi9A2+?f94sMD+eKC&hfQaxjyzx=O*PyD}zN)IFkS^?7 z5`7;K;WLV$%*)O^%i*gefjv|V#vlSoSzieVbsA#Cl88MdAR2{KnA3*@OpOtv zpxKb>>n6-kriz;jL!t!t5?b+lnFKi^@EL@N^#&MGrd}_H>ez?a!773DA|g$vZ~VG- zd3D0MmWDbqxrA&~X1j@Qf&lu8$1hCAox^TCJ}?+kd2nL82@SjiS?^d`{F$bA7XZC^ zArf*R|JHE34807~5*}ri^FK1Un+4l16e+RjwnnRU$oR@)#_H`Z^&aO3y=bUe?yIs( za6n}6*f@HZJ<4FvZ5<75mi>s(=<6FAd$+OC=mkWX7B=o9(Ok$4gvCcW%;k;)f?%OE zM+uwQAV&kweU(^_#*nB-N+KoIU>kDi3(^`$~|K;dVwmThm`vYRbLGz-nzc2s*002ov JPDHLkV1mr-b+7;c diff --git a/companion/src/images/library/00017.png b/companion/src/images/library/00017.png new file mode 100644 index 0000000000000000000000000000000000000000..678355ae01046bc6cbffeb5154ee2650c372f43d GIT binary patch literal 634 zcmV-=0)_pFP)|ghCdPFCGFgbg>Lc(dN2fR7u@u($Og1kDT= zovtbZru$vw_GThr?df*nTOttL+sSuJ1cHv8tSk|5xxb&>^equENPmrc&n*!kIRGlq z02%`<@S>{@CQsEUvBzN>xg%rxKtXX3J-)ITxb0E5ejNHAU_T_ zu5aY^8b`=32CgzxvkwehKmgFi0)fH+z{(6i;YF-ikHW;WY@?f=aar%O|GP)&>F*Jg zUjQ_co_G-AjF-L@QV^VZFkkMX Uh5FI?1poj507*qoM6N<$f|Gd{F#rGn literal 0 HcmV?d00001 diff --git a/companion/src/images/library/10001.png b/companion/src/images/library/00501.png similarity index 100% rename from companion/src/images/library/10001.png rename to companion/src/images/library/00501.png diff --git a/companion/src/images/library/10002.png b/companion/src/images/library/00502.png similarity index 100% rename from companion/src/images/library/10002.png rename to companion/src/images/library/00502.png diff --git a/companion/src/images/library/00503.png b/companion/src/images/library/00503.png new file mode 100644 index 0000000000000000000000000000000000000000..1ba8ec880030f99ce8060c3ef8aa64a47ab22572 GIT binary patch literal 445 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 literal 0 HcmV?d00001 diff --git a/companion/src/images/library/00602.png b/companion/src/images/library/00602.png new file mode 100644 index 0000000000000000000000000000000000000000..ac46509c27ccc8bc3ed1accc36a570ad29dd8792 GIT binary patch literal 563 zcmV-30?hr1P)&Y z3l>mN24y|~d{E7-0^{IztQOL{~Jq^zzb2TA3 zL*Sf2!mtmo0XQ3gNJqbXNl_z;nFUI5FmWDN`SAGTV~R8+>GKB`qi7OI2PUE&kw0^W zV(u5k0XSuTBi-wOKnl=9XsbGdI9rY*p0+Cr%Rm{dy%>bG;?e=gn7tQpH3TR9nTtsZ zj8&TOq|L}GMK^ml#JavPdO0nu5c2_mb#|lh3|MD9jJ_c$u1T~40MA#$cmV3$8SUYj zuZ;*?hg4`xKLaWX814t|bo1N`5CA~0zP^P@?iX)w!K&*%-^=Px2f$zeTAP7)ieT_8 zcol*e3_#y1SPb9|23VW{{VNLin<8Y@-}l)({Q!jMm4~{1Ng4nE002ovPDHLkV1ml1 B+FJks literal 0 HcmV?d00001 diff --git a/companion/src/images/library/00603.png b/companion/src/images/library/00603.png new file mode 100644 index 0000000000000000000000000000000000000000..0fa584dbbc557976e3d854c50e64d0b5ef86a976 GIT binary patch literal 612 zcmV-q0-ODbP)-5TRKCIPg#3-#`a3LXgGLeK-i9S+U14HbeM0IuLI>jeTM0F?K`IEAJLfV%ui zAQ;V(JpZ_3VR%Y|8o;3a@e%?6;OL%Hkfp_k_aA0icwPub5O{oukW>M@)1nH_iYGia zqyXSc{xJfZSg}R}ZcQs46kti>Jq`iek023_jNnq_XbZ`LE-XmMlJc9dfOsdIBIw~U z3_u^6H)BbW>|Y+lG2n?P1pFBQcNDZLVEscDl>Cdm)8!;7NXAzxxZ2WWkq9PjancCQ zbwgV=vdneXuIM~7%Zd#fYi^n%`Cwv0EbqxVz;|5Vh0d0Prem;7Vtr0>Nc^iA8TTYa z?uHYO#=C9)KRTZ*K(B!&<5;+*4!~V)uJ$6kVwj(V!U0s8x$lUw)Pvf}$84jd-Ury< zv{|8&0d8|s&!=*f2XI733jzR|0SiiGR?ONHft%r2I2Y6-kl&{H|56Xv7H~X2(N0EX z64|aXi9LWu523fB6l6nZ7`Q|T?8X*(M>HzHBM4~81_%se;F}RK9oAq}TfW$n4jj?o yAOk$&1E-A$hXLUI+v6#SIiT3+F={x)st!J-PN9O0)(0N|0000Px#22e~?MF0Q*|NsA`*`M720004EOGiWihy@);00009a7bBm000XU000XU0RWnu z7ytkO2XskIMF-pi1{O8~v|4;)0000TX;fHrLvL+uWo~o;00000Lvm$dbY)~9cWHEJ zAV*0}P-HG;2LJ#9*-1n}R5;5;lfi4#P#nj9X==kTCdfcr47P}L7Z2SE8ez1>gS!-Z z@E?c}x{GLVJ4`5RwnFQn;2@WUbxlv6$Nqwh$Xv0s11~!aOmG+k57Br?rS$o-Ch6$| zUmm>g`~5x-Mp~gZcI^nzVv@XMH6p-@*jKV;H3AM6lx#_jfP=A;t*Ci)4IDI?g?+(P zTfq8gGB8Z1I@WLX5(po|G)(IV*$6oRKBjdT;sQTi+XPs}7~&o@$4e)M4v@rX(P0lc zt+PRocwfns58$suWpEIOm0Dj}8gz-tCAlXh1PsPO{83jLfn@hCO<3#r{!_>&E;woGo4lXPGUo zo$!OcJ3C>%qW2jQ@-(-YJ8>{Fo7BZk8uFb&{;A<$2-~D{uLEd;YmA)q1nG!0ixU_f z;vQeU^dX+dj``*=@Z&wpq-00d*TNp1g!qN{sLOvsKRTqy5LtmZ4*lp7R}&Hkksk*z zl@fwO&i%lZvmXe@e{JXoDo#lk5oY9vUFpU)|B+5H^uuV<3BF2Q z+@JrKty{{YxIguoA8JfW?eR38Q{abMkWz}nbrYcF9n$OCPUwd{lBYG@we@d-9|lEqmSxK*y$*XkCi@C8P=$wqA3MeA*dvS5cu&uLf{9A@E_;!>ge~HvKjyY002ovPDHLkV1gTmj_CjZ diff --git a/companion/src/images/library/01002.png b/companion/src/images/library/01002.png deleted file mode 100644 index e83381a48ce269eac0fa3ac72a8a260854c1c768..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 855 zcmV-d1E~CoP)Px#22e~?MF0Q*|NsA`*`M720004EOGiWihy@);00009a7bBm000XU000XU0RWnu z7ytkO2XskIMF-pi1{OC5-7C4R0000TX;fHrLvL+uWo~o;00000Lvm$dbY)~9cWHEJ zAV*0}P-HG;2LJ#9p-DtRR5;5`)6Z+uU>LyhXKlJ{v^2sFZY-=lNOqH~Ihf)|J$Z`s z9}w)IOTizQ;TRJutu3q`iVSnG!Oq+~kDWY-Bvht_k`6q08>s_};9+Y#v=H|Cwq4)! z^o55&p5**8LsoHA4)n(qm%3RA~s*pm+MF^$( zu+1Pdg&=K6+xSPMYw&N$HJ=*zTUasEY3%VqZ?RLn>;I1oV@K~5@g9L}a~}@^=2C@D zLn#Xqe&V;Rr;0CV%MN|XLP=Q^xs7rePN~eV`H}+1IWez1t9+aJOzrM4$2mY~fY&fC zXZp0a9zzJO4#W;i9DJPTpo*$^Ti)FmO=IO9cFPMWucIv@|P(MIQREryB=@}PZy z_xRC00iGR{>Gr|I$3Cdy7G3duh;SmTQVrk7`pmw-$<`6^aqH|{xDj)Dz7LMyeas&! zzK>M={$Q}CEvhjA>hjuFKN4}4|rM+wE zJ>LgqtsM?Sd{nJ1aTwwQmEFQH#D`JZc|HvB!Iah=9N)(#UH>?`FB2b|p&C{ZAU>pA zsHWf$A0>qyXX4{nncL-Xh!5l?FNPsL+I6WgzPDFC=xBZ%vd2UJ-i~}Eo{U3$By!^r hA0!hWBoiMb{{eNl>eronMf(5%002ovPDHLkV1h(=bRPf! diff --git a/companion/src/images/library/01003.png b/companion/src/images/library/01003.png deleted file mode 100644 index 88f5676db725a9fb3bfc931e39c826afb2cd2403..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 840 zcmV-O1GoH%P)Px#22e~?MgRZ*00010!qa{L0004EOGiWihy@);00009a7bBm000XU000XU0RWnu z7ytkO2XskIMF-pi1{OF3!@Bg?0000TX;fHrLvL+uWo~o;00000Lvm$dbY)~9cWHEJ zAV*0}P-HG;2LJ#9l1W5CR5;5`lfi4#P#nj9bz9$rxK;(ppr(4!OOez{w_>Q<#jF3q zW0llHnS~upVJm@v3J!DaR=0ZbKFmQcx`fHPLuz(xP_{r}J6Iv5Fbmz(mu!8>A$)jW z0`L2N@AH7ih7x613XpooO_f`wfL1+QvNe%{1SchXTcjXCv}A9I6j14%6dOsA0@BV= zftwO3AR+^>5JH+1xWTY#Y@Gw7ey6GC1*t#y<0I&S6Sh`7BijzMr9%=7b>>i8yg7uH zk}b6}VoQ;kc1A)942Bs?)r7$iV*fP$(h%IGw2CsUTLmtb!Bb11126!fPr~vf%*_I9 zVdD)M#Fhjm$LM8D&eCZ%IHBT>ohCWC63oMy`hG=|$!X8(+2OU&Bn-)~b6kU~ISQ2U*6}aGN8+drShe z-|1TU{C)x$3s=oPm<7Y!6%zZikl57)vj8yW?G15=$3bSuieDf-QY;Vrb)<~*3nM?u zP@YlI%fOE|xTzm#C-B3JxT%9D^MM~$C!YGr;*cN5Zt>lta>$QUr!aj_3j1+u?wT{1 zmVpZD?A%{X#6x~K%@1FNcG!>ZFRi!{@?)+`@FnEOe7BYne~0{-x3+yvMt&?A>Rk`i z4^U#*1N8$dZy$T0e)N=YhaQ3+(Tn#o@}nMo=7ah{f{F*~$9i%vM?n3^ZN_Rj0_q2h z=dU^h)DQmY?Z)}Lz3^l3x8Nh_v3^3|t?x%`IcQh4~mf=6#oI64CP@@ S@WkH$0000Px#22e~?MgRZ*00010!qa{L0004EOGiWihy@);00009a7bBm000XU000XU0RWnu z7ytkO2XskIMF-pi1{OFj7y&&F0000TX;fHrLvL+uWo~o;00000Lvm$dbY)~9cWHEJ zAV*0}P-HG;2LJ#9y-7qtR5;5;lR-<{U>L`r*LO>VWm*_WiY4{~cz8=8RhD%n>E1Vufd-uJb+y6l-vcbDg?E+94XpvI zF=`>?{NH71MNm$HjLE!5#oVxk zd5=ieN4*L}Rc=Is2nJ1AzshTnT{T*is2C_$cY>MKZW1b%S z)xEhNh7jJEEz@Rx=)6@xo^3KeK49w(c|KbBfvgPnz9QyF1;R0ZNig#x-YqYQ+`^A| zJ>s%}l6k~_JmbVCg!xg8{U99kL%Rl0ye?*bXhQ&fM0+ql1~XH?vSH!JG%|Z~H80LNy8RmXu80LN~@E^Lw(Af1?YLEZ`002ov JPDHLkV1i3nh%f*E diff --git a/companion/src/images/library/01005.png b/companion/src/images/library/01005.png deleted file mode 100644 index b4aea5dfe4132fcd477107f168d48dc90c073a3a..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 883 zcmV-(1C0EMP)Px#22e~?MF0Q*|NsA`*`M720004EOGiWihy@);00009a7bBm000XU000XU0RWnu z7ytkO2XskIMF-pi1{OIm`xP-P0000TX;fHrLvL+uWo~o;00000Lvm$dbY)~9cWHEJ zAV*0}P-HG;2LJ#9y-7qtR5;5;lR-<{U>L`r*LO>VWm*_WiY4{~cz8=8RhD%n>E1Vufd-uJb+y6l-vcbDg?E+94XpvI zF=`>?{NH71MNm$HjLE!5#oVxk zd5=ieN4*L}Rc=Is2nJ1AzshTnT{T*is2C_$cY>MKZW1b%S z)xEhNh7jJEEz@Rx=)6@xo^3KeK49w(c|KbBfvgPnz9QyF1;R0ZNig#x-YqYQ+`^A| zJ>s%}l6k~_JmbVCg!xg8{U99kL%Rl0ye?*bXhQ&fM0+ql1~XH?vSH!JG%|Z~H80LNy8RmXu80LN~@E^Lw(Af1?YLEZ`002ov JPDHLkV1hjaiOv83 diff --git a/companion/src/images/library/01006.png b/companion/src/images/library/01006.png deleted file mode 100644 index 448f590da1b08ff028f1744fd89997ecaab1e31e..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 840 zcmV-O1GoH%P)Px#22e~?MF0Q*|NsA`*`M720004EOGiWihy@);00009a7bBm000XU000XU0RWnu z7ytkO2XskIMF-pi1{OLb%HpQ<#jF3q zW0llHnS~upVJm@v3J!DaR=0ZbKFmQcx`fHPLuz(xP_{r}J6Iv5Fbmz(mu!8>A$)jW z0`L2N@AH7ih7x613XpooO_f`wfL1+QvNe%{1SchXTcjXCv}A9I6j14%6dOsA0@BV= zftwO3AR+^>5JH+1xWTY#Y@Gw7ey6GC1*t#y<0I&S6Sh`7BijzMr9%=7b>>i8yg7uH zk}b6}VoQ;kc1A)942Bs?)r7$iV*fP$(h%IGw2CsUTLmtb!Bb11126!fPr~vf%*_I9 zVdD)M#Fhjm$LM8D&eCZ%IHBT>ohCWC63oMy`hG=|$!X8(+2OU&Bn-)~b6kU~ISQ2U*6}aGN8+drShe z-|1TU{C)x$3s=oPm<7Y!6%zZikl57)vj8yW?G15=$3bSuieDf-QY;Vrb)<~*3nM?u zP@YlI%fOE|xTzm#C-B3JxT%9D^MM~$C!YGr;*cN5Zt>lta>$QUr!aj_3j1+u?wT{1 zmVpZD?A%{X#6x~K%@1FNcG!>ZFRi!{@?)+`@FnEOe7BYne~0{-x3+yvMt&?A>Rk`i z4^U#*1N8$dZy$T0e)N=YhaQ3+(Tn#o@}nMo=7ah{f{F*~$9i%vM?n3^ZN_Rj0_q2h z=dU^h)DQmY?Z)}Lz3^l3x8Nh_v3^3|t?x%`IcQh4~mf=6#oI64CP@@ S@WkH$0000Px#22e~?MgRZ*00010!qa{L0004EOGiWihy@);00009a7bBm000XU000XU0RWnu z7ytkO2XskIMF-pi1{OOI@=bGQ0000TX;fHrLvL+uWo~o;00000Lvm$dbY)~9cWHEJ zAV*0}P-HG;2LJ#9p-DtRR5;5`)6Z+uU>LyhXKlJ{v^2sFZY-=lNOqH~Ihf)|J$Z`s z9}w)IOTizQ;TRJutu3q`iVSnG!Oq+~kDWY-Bvht_k`6q08>s_};9+Y#v=H|Cwq4)! z^o55&p5**8LsoHA4)n(qm%3RA~s*pm+MF^$( zu+1Pdg&=K6+xSPMYw&N$HJ=*zTUasEY3%VqZ?RLn>;I1oV@K~5@g9L}a~}@^=2C@D zLn#Xqe&V;Rr;0CV%MN|XLP=Q^xs7rePN~eV`H}+1IWez1t9+aJOzrM4$2mY~fY&fC zXZp0a9zzJO4#W;i9DJPTpo*$^Ti)FmO=IO9cFPMWucIv@|P(MIQREryB=@}PZy z_xRC00iGR{>Gr|I$3Cdy7G3duh;SmTQVrk7`pmw-$<`6^aqH|{xDj)Dz7LMyeas&! zzK>M={$Q}CEvhjA>hjuFKN4}4|rM+wE zJ>LgqtsM?Sd{nJ1aTwwQmEFQH#D`JZc|HvB!Iah=9N)(#UH>?`FB2b|p&C{ZAU>pA zsHWf$A0>qyXX4{nncL-Xh!5l?FNPsL+I6WgzPDFC=xBZ%vd2UJ-i~}Eo{U3$By!^r hA0!hWBoiMb{{eNl>eronMf(5%002ovPDHLkV1l+{b3_0D diff --git a/companion/src/images/library/01008.png b/companion/src/images/library/01008.png deleted file mode 100644 index da3346f7d7751a316dc2cc1085f479b76368706b..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 911 zcmV;A191F_P)Px#22e~?MgRZ*00010!qa{L0004EOGiWihy@);00009a7bBm000XU000XU0RWnu z7ytkO2XskIMF-pi1{OOzUh#@10000TX;fHrLvL+uWo~o;00000Lvm$dbY)~9cWHEJ zAV*0}P-HG;2LJ#9*-1n}R5;5;lfi4#P#nj9X==kTCdfcr47P}L7Z2SE8ez1>gS!-Z z@E?c}x{GLVJ4`5RwnFQn;2@WUbxlv6$Nqwh$Xv0s11~!aOmG+k57Br?rS$o-Ch6$| zUmm>g`~5x-Mp~gZcI^nzVv@XMH6p-@*jKV;H3AM6lx#_jfP=A;t*Ci)4IDI?g?+(P zTfq8gGB8Z1I@WLX5(po|G)(IV*$6oRKBjdT;sQTi+XPs}7~&o@$4e)M4v@rX(P0lc zt+PRocwfns58$suWpEIOm0Dj}8gz-tCAlXh1PsPO{83jLfn@hCO<3#r{!_>&E;woGo4lXPGUo zo$!OcJ3C>%qW2jQ@-(-YJ8>{Fo7BZk8uFb&{;A<$2-~D{uLEd;YmA)q1nG!0ixU_f z;vQeU^dX+dj``*=@Z&wpq-00d*TNp1g!qN{sLOvsKRTqy5LtmZ4*lp7R}&Hkksk*z zl@fwO&i%lZvmXe@e{JXoDo#lk5oY9vUFpU)|B+5H^uuV<3BF2Q z+@JrKty{{YxIguoA8JfW?eR38Q{abMkWz}nbrYcF9n$OCPUwd{lBYG@we@d-9|lEqmSxK*y$*XkCi@C8P=$wqA3MeA*dvS5cu&uLf{9A@E_;!>ge~HvKjyY002ovPDHLkV1hY}j;8! z_w#AA!!1XZV^_WT`xeGDTyZJsl@_1>qSm43&(5Dk9FIDd&-XpIcl%>m8HQ)q-XCvJ zVg9_*NxozDUiRs8>J)BWY+u%t#vsyXudVTc>4WLxpYHC5)~{lkCm~Uv>iNTN4MXhP zTb{Dp8S8UcK8OdIPnTiZu}QLl{nn4Br%ZJ(+Zc`-$}(hoe7fnwt=amhbP=QZZWa3} z=N?)$3s2VH>~JP;tEtJ{!)on~m!@hm6nh`&>GWN4t2I^rzzrdHA8v8io0o;Y@SXJU zkS)L1euSyn$ar=3x1N)x7t0=LGGA=eI_0>{Xi-CqSbys8r@OnCCRknm#rx=P>|N$J zYk4_Cx*x7)iBA@^VKS7x$G+aamrLV#!R~tk?g~u%V(UN3|G3HjNc#6X7mhXS%2T|5 zD`kXty((sXU>$c|eroev(S(lp*}vLY%$QE_D{RX-CCiy)_hPw=?rgt>JQFPJDy)nDPRP2EDPG_;0 zhuc_;)V!{$tXU-M8vS%l;j>-d|! z5_u=He--d#bv0WXPI>a9=k9{H2^?{rzBNX#4i}3onal7;U_tqk*uV{(Rs3?>ZKE46 zGQXd~bSL?H1D~;VPbZ7tq}>TS<^M6t81T##@w}7+Ono9Ht`Q}Ur6n2pMGTH9MVX0t z3XZu+sYU5^`QcGOc~OwObAE1aYF-Jdg8od813(3;AO$IjC8<`)MX5lF!N|bSNY}tn z*U&V?(9Fuv#LC1>+rZGuz~IVU*>5Nsa`RI%(<*UmSbAWo7f=I(r>mdKI;Vst0Nb)# A+W-In diff --git a/companion/src/images/library/10004.png b/companion/src/images/library/10004.png deleted file mode 100644 index 1a93226b7a413e5ed42bd7e37de839fca80a7e83..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 752 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxPeS=2F54mYxgrS zF#h*+aSX9I9ec?)@3MmkdqKOCx|3>K?F*5w3@X-3+-Ayl@X9Pwf3a?b;N(>un^t@f znh>z(34<-eG%dl6T^5eZ&mQuAQ)Mis|GDCug`D-YWAgTuHs}9W%H_$#RbDF+KEjr8 zqpg1S{fN9nG8NKH2^lHe=LB3HC476pnI+dPwXZt%%%P*_rS`4-{ix*H^L2e0)mLV& zU6*}A>Ho$VYn|A=N8W>JrN)`rWs^&j$IV!CD6Fy1vhiH~B!*Z2&8D>I zfQdT;4##gZ_}nI{@Vde0y`1fnUXJS2za|l^dzzL6`)Vq>?P*l|<7%^iYOiLSxekzI~E$ z*~J$|jHeDTt(AV8qw1O+wP4GE(+3;{H4n2~M^4?tYDMEy zg0|=nUH0D-d9yZ!vmD_3$9(3L>+a9TRvZ8(3Xu}mh!V%rl8pQ!2FH}5%)~qe$K0gU zqV&4_@F<|XC`jHpKQ}iuuLM;=f2Ie>09BBJl*E!$tK_0oAjM#0U}&UkV5n uWoTk$Vy10iXk}n9{awq9Oao<8L3w2PRM;o6f~&_^8t>lNWpFk5a7NRwnB*v7CQ+k%u@@^AM=8kc zc*8bR;#K!F`MV!ar7{(AJ+RK-^=EE_!Ym8+eYR8H-u`u((`;Q^^5(#GwX08PsMLQx z{n&3}^{$jC6Xn`#me0EGtWTZ6axLckf#!KJDF>Gctp4!q-Cp7KN^J8Re0BG|-aR!$ zRfuK!yZjkz?6n1(=j?dlcR#`B!hYN!0FU~b*Y=2d&o z+O0lqv??q_@r7x9)s4LmW%*8vvRS7v*517EjQb0ni6~a@?vhj{UHi?;f>^L#BIKZfl)VTxE9j^R95Cdz&;CN#392c9tyboqlo|0w=G_icdZNB zS=bksvg+@L#-kEGDSu5i-MIhjo5Ac&>0X>H-Yl>4(k9dfXwJ(O{9`7&(tf+ZlEt{D>`CllL(81>Szv z)W7AAoKyRRO9$*9i#bi%9d&anFm;NQxJHyXmX>7X7cn@d6lEsnDLCdPr52^v<%dTB zlW4geLXf)u1AmZVxG7o`Fz1|tJQBV7YST|?6lLo+Kw6Dt!l oZ39Cq1A{AbWxt_l$jwj5OsmALVd;UTUO){Dp00i_>zopr00;|>uK)l5 diff --git a/companion/src/images/library/10006.png b/companion/src/images/library/10006.png deleted file mode 100644 index ca77bbd870eb067a10617e107a494c4be51da04f..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 677 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxPeS=2F54mYxgrS zFmCa5aSX9IJ@@i{FI7Vkwhs}xn+gFi?Z_MZ%SbM8b&oHRBZ_%##f_X0wa`Jq6^*=&lZi{Ng z;uZRwYZm!5P0PFyk{oa$Ou?ghxxL_=wx~;iX0m&96`r$X9gsC*xx#Ymp<46Dg^C7p z;hb!blMDi8`-il=KlY15?}2;XL{q({<7bw*d9TiG5e%I!6&o!&S?Nq)_0;VXt?q8z z`@F<#ZAF7uf#cGQ8qWA;p9OnYT$*(Ja*giUY)i@VxeGUE@P980duiV#GBY9jH^aS@ z1cFX$y4!5vyn-`9dbcGc@?~si*lIelL6FSVhG6d7DE-E(`U3)5yC$eNjp5 zt;NM$-=f54r diff --git a/companion/src/images/library/10008.png b/companion/src/images/library/10008.png deleted file mode 100644 index 9616e2c1204ef388a4ff93c2acf27225cf9a344d..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 606 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxP?KOkzv*x2?hqn zTu&Fr5R21uFB|$DF%V$AkYA~4-VwuaGCks=(o=&u3A=R#Jl#7j7{fO%@Hi>D$J`*c zOXJvMN$WzdOK+aNt@>y2SV2zDqo_3(%Ji4sg!ZGrL!7B;l5c^l0UWV#@I#?n_kjfsuV`kAyH>=!$+ z#D^bYdz6v1a^nAYXZ&?GzIDrSJKY85 z9=7|%iS% z4z7Ry&0D6vd+xN;zbqneEnHdfZ%h$Cl;PUFW`=&UTq+ zy*+McA6S^*m?X7e2HOhOHFo`Pd; zQfg6pU4D2JP+k-y@0_2To0?aGs-Qp9;{Z^BDo8;}Vo9o1a#1RfVlXl=G}1LN)HO5> xF*LI>G_f)<(>5@)GBCI@SN0oIKxm;OXk;vd$@?2>>9R??eCq diff --git a/companion/src/images/library/10009.png b/companion/src/images/library/10009.png deleted file mode 100644 index 1919fc94b08f73839baf30835bff07aa695930f9..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 653 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxP?KOkzv*x2?hqn zIi4<#Ar`0SUN+2oqaeWcKz^f;uSn3c;=T`F<@>t&CtPwBnXHyMZ<6v8EsgazKE*bk zjca(jY{N8$hckR|_hPM4H>v3_fw`aFs+{=ZpT39n#;}cx^??%*4hg?v2J1 z>=rvQ^m8UMA6yZT^yFpOUw+kGnP%tQDZTG!6_u_~oVOrb+p;BN@76hs88r4+;@Bd#XA^YC`Ab0JLilhox=Ouo@?>}T%SMRLV&&k=A=WvO~?y2qu4dY<1%l|CT{9G36@ap3p*6xQ)F1sG? zIvBa+-->QY_I(#-+gmUF$#^3Cib(U?A9=vY6De_xC~+(;$;dBaa7-!6Ow3bo%uPxy zO0UZgj{?ezg5;g^b8}PkN>CN_XL=j}Do_O}NJ%V7wMs5Z1yT$~28Kqu28OzZrXhxA vR)!{4CT7|OhE@g!SLVuoL(!0%pOTqYiCe?c153St8W=oX{an^LB{Ts5!hZ-! diff --git a/companion/src/images/library/10010.png b/companion/src/images/library/10010.png deleted file mode 100644 index 0ef8056453025c883b384a240761741398cfb216..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 645 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxP?KOkzv*x2?hqn zDV{ElAr`0SUbgi+Y#_q^q5g?ioWMSZ(AC>dG)yrrJ>B3Dk>L20Bj#w+Lgny+ldN~% zD!Q6(n?JX|FJjfIKT`Yue|CSE&lcwYJlf!YL*K*KV!!m7b0vD_J(zP~71J*N2S->! znY1Fm%}aEd{LoKjhf?^~34e@Knwyhe9Oab|xp1O*w&{+Ts|yns#7wK^a0nA z`G$?`{bF^j`=;-^;;~-(=UeX_iQc0n0ctkdUUw6da%$pw;EVF7yUmoMC{@$~}CJULi2X;BlkU8w$*}KJ3?fO2g>B*;7*7aDX?F)J^ zcmBfoHD>QSW163SJ?|i6?A#X_6QlF3L~t|1>?E-Vm$EKgza+F*%PQa$uYymtWoCG> z-o4C<)$RVaHZnmzEy=aNGTYwXJMz@EVp;ihUhBkUy z{gaA?;R4D37#1)1+;eWBq8TvKL`qyEN*qf|GV+TU98-!i6Y~@tbCXhw((CfWqk!_F zAbIEf+}zZ>5>y5KnH~p#3RFP~QW8s2t&)pUffR$0fuWJEfuXLUX^5ejm7$51iJ7*6 mp_PHbmASItP&DM`r(~v8;?}VAz)~-u1_n=8KbLh*2~7YO76lLh diff --git a/companion/src/images/library/10012.png b/companion/src/images/library/10012.png deleted file mode 100644 index 6007e75d4b1e09ca000f3cb48dad7e8175a38532..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 664 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxP?KOkzv*x2?hqn z<(@8%Ar_}&FWYzBF%V(t0w;U#I z>^dM4-NUB7py9*m%ai|~c${|3{_*?Ts>2O0oW8OyT3j=8%~tDz|98A2zT1 z^YOC9wFmFdTKtQ1;&*v&ZQfV!9DTsr%I7PN@Z4Y7DOg&YgeDbA|C)N#*~_hz0C- zK79GLuBlBzu1(kZ;)jP{AHKGl*3R?pADpe%1=DGm0_$Za>|! zGvex$_C0q)pDX?e+wJ%uYM^r8UQA`&Fx!y|AAZq;oRk@bTlocoZpdjVN&}Ey>6) zVsK0;%1q2taLi3gElRJ;503)Mi-P2x^K)}k^GZ+^^k;e;04h)gDM(2yNwrEYN(E93 zMh1pPx(0^2hNdBgW>$tKRwicJ28LD!23O|FenZiao1c=IR*74~(gRDqfEpM)UHx3v IIVCg!0BBAUO8@`> diff --git a/companion/src/images/library/10013.png b/companion/src/images/library/10013.png deleted file mode 100644 index dc8a5efc703cb5933cab1e469cef8f7e05442616..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 612 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxP?KOkzv*x2?hqn zVow*x5R22XmksldCwHA-RsMci85#AVKP__KwhQKq zUjN;qvp-Sif%>jJ7jk#9hBlbrv2`ttHso}fta$gYz#4~3C7v!auck2YGTl-BXe{~c z<*$>=>wUC)8aB^!<_$lt@W8ibiN&X<4TjBg^t}(JbU6RryUHMCf)lHUvtCO1gn(IR zIp4n0BDF^Bq*x%nxXX_dG&EIqK)3#fs?)78&qol`;+ E0Gf*OWB>pF diff --git a/companion/src/images/library/10014.png b/companion/src/images/library/10014.png deleted file mode 100644 index 6a306d3b202728fd581005cd9a9bd36b7e65644a..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 656 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxP?KOkzv*x2?hqn z`JOJ0Ar_~5FB|6FHjrR_pkDCc#KP==*oDb#%2vS(w>FdrFz)NJVvT#mT@vtsNy@6F zFK7xY$G(3{bUHtU^vSRNZvVHtg2Bp58Vy=bv*tS-bSZFcGH%}F+7hBM zWf@PG)XUZ-6D}Xux>L1b>XrSEy*E4MSolgtxcup2RBm@Rl-6&$zUwK~N_cSZh7USdYdz*5Og{rRN{k0>fpxH5xeQslO zVIik>MMi@p3xgK>wuYOI{3hiAAM~8x9$>uDcr>;x<=kGe2`hhZ+@Y=JZ1;ZEX@SaB zw+?u%Rjj}5_)nrcM}F^}UpxOW`SRRbaCN2kwkMV+-W+s%pXhhCLDRH-$}DHEvj-jD zDu$kJ+)?ZB`lV_q`?qhdsaHk*Gs@^`E3bbXcMKSRA|2>+xQ9yZ7ki2t#Zf?)FK#IZ0z|ct7z);uF yG{n%%%Fx8h#7x`3(8|Ez%3RrRC>nC}Q!>*kacfw5V5t{S1B0ilpUXO@geCxd(h3d$ diff --git a/companion/src/images/library/10016.png b/companion/src/images/library/10016.png deleted file mode 100644 index d02cb5cebf08d7dfb0546ce4aa9ba016aa84d64d..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 601 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxP?KOkzv*x2?hqn z3{Mxw5R21iCmZ@5F%WP)&Na!}$8)37^&5KO4>>LbDyRzC-f7s(QaG`IdHpue#HYr_ z-;RXsV9*S^r~cpG*j`wvC`0~Hx<%81_R<%Cc7`XL>;HJFZN9LZVY#XJ2&UCGv8e;R_z5o5Db2)E0 zybt(R-n0@B04L+YCI!U^Hb)OC}S<_Cn>c< zj4jG9_!H##80s1RG5%mJ+|YJ$*WYM+U_^+NxJHyXmX>7X7cn@d6lEsnDLCdPr52^v z<%dTBlW4geLXf)u1AmZVxG7o`Fz1|tJQBV7YST|?6lLo+Kw s6Dt!lZ39Cq1A{AbWxt_l$jwj5OsmALVd;UTUO){Dp00i_>zopr0OhysRR910 diff --git a/companion/src/images/library/10017.png b/companion/src/images/library/10017.png deleted file mode 100644 index 13f6ed48172671322a41f177957953aac266b7ce..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 659 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxP?KOkzv*x2?hqn zMV>B>Ar`04PPWZD>>$wUezReh2D`uuskV-siHELp{9t(%!?9$7QmoIf37c~aj$Ds; z%)O>y^U*~o&vXyqwK;>Pe^W_vy{& zU$-&lIDefS{(Q~vTOBNy0_J{-4KI2BokO>=Jz(aBue+>OIHny)UYWB}VvkbAzVF7R zJGpw#b9`Yj+wl6cmPw;(2FIN@en0I@PWVnVk^WkkqHtX)^UKqt(@O7Jn6)jrIDOih z>AmT%JNovDUM}cxJfp|3De|A2_ni72h9YKXeHXXs@;R8C47kw~b&Y2&OUE<5C49?L zo~{tQ!Es5jg`-Q*M@qI)lF{u!`~Qx{ShG32&we|&gaiU&P>;Qk0pP zr{I{Ilv_j3Q~}gSdwa$T$Bo=7>o=IjdTqR zbq!5J49%sc)I$ztaD0e0swLm B2vGn4 diff --git a/companion/src/images/library/10018.png b/companion/src/images/library/10018.png deleted file mode 100644 index 552c9654073f98078125965661f272fb469cffd7..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 712 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 diff --git a/companion/src/images/library/10021.png b/companion/src/images/library/10021.png deleted file mode 100644 index 69ea3ad1491c7f06c191beb454c8a70a341c1066..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 744 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxP?KOkzv*x2?hqn z@18D>Ar_~nUOL!y*+GK+gJv^}zVseV5%>EJAA$_uaM(5UCpg;ZUuvG7I{AU3c;eS* zP6quCxH;Z#Y7Y|l#H8oRG2^h@EQt-lN9z2Js00v^G8&1vI`q` z;*3jcw4_exZad){Y;bb@QO<`;r8c>qnfZX}dS(RUpATta6_);ti4zhwec61)cU_US z^OB%PK1tfXFH>Ixn>FfGh+M1yXZ+$?3Mx-N5Pn+&G!!V zE3Uo7!nY(R(WNjh{KWg{3H^3gyu&7haUTi(E|3s!_~FW5wq0DWP6lq}e$uRaz`%U@ zx0|u{Qe8!DE`|2O@>RXOG|2mkx zez0wx(DGed^kQsdw(r`)EYK3h$giN@yn?;_&`(7VBMxKPcY49R$4VlzavyI`Hi-GEwWeqRW6H}LQaO*5*D+2J%sB9|{pEsv``#TCmpyTK zde!Y25>^Ku{$SrF8nXGd&HV+ybRkmW8d2g{T9T1p#Ne1xl$n^P;Fz0~T9jUwA07pi z7X`^X=jZ08=9Qo-=+E>x092p~Qjn5Zl4_M)lnSI6j0_BobPWu34NXG~&8!SftW3xY4?Yf2i{mQ_|DguZpFIB-<-#;Q0ui^;j4(pO$V3GU9~Gc zqOjJ2dqQOCIrSVS8H19@)jI6Yc4$9gELwc0@7dftLPrxsHUFEmTwlE|A!GXviD*OD%{w7`r{jKVf99G$^J>U3uZsD6U zg;9uk`%#10LhCOWuuWywblou1G5&+E%{4a$cDAr^hl$}+*j9*dPz>eUGTHNwq~1lQ zJKz3(Wth*R)5fFC_HM$zxH|`{b4*^P)v?PTbpE|mPVwpgst4J(j`%5lHrny+r|pr0 zSAA_8gnt+}ozG{jdw#a4!S2weNZt*d4bR*TtmLqN_t5FVb=x`o8#*q$EMqWsFl17S znDdvv@UP55`Tc(kf*JSybP0 Hl+XkKv*l3~ diff --git a/companion/src/images/library/10023.png b/companion/src/images/library/10023.png deleted file mode 100644 index 784dbf355e5a53e57d0a1fab0094e1ae43ec2a23..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 451 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxP?KOkzv*x383I5 zPZ!4!i_>Q>Z{$6!Ai#Q|e}a?eY$YMNgVGgKdnOpUsu)YfUUN9bq^CK7vorRCe^^TS z&QGG{$Jqm1675yg6E^Xj&)`UtHE|3RV36RvW5VcnC?UGzfU9{xG=uIE{uOL$7W^gx ziAs(QlNz`l^LJD$e7M0kPmFu+r)&l8AM=D~7hV<#IQG|N!Uv1sB;huV1@q=DyjH-m zZ{jxFBKCbdYg%{Q-oYBxl%?qL;RWl8GYoqfO<2`F%NZEkTjg`x?@H*F&kPQC68xa# zksb5&g81+13g)28E|(wJ7KZ?RCsN`XQQ}xyl96A;;FwaBnV6^Gn46SZlwOw~9tD&a z1<5<-=jNv7m7pr<&-6F|RG2bOvPH86O(`njxgN@xNAELfC! diff --git a/companion/src/images/library/10024.png b/companion/src/images/library/10024.png deleted file mode 100644 index 4066cd8e0ee207c2f5c862366d0e07a3f95657d8..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 555 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxP?KOkzv*x2?hp6 zD^C~45R21iFI!JKtiZ#TP#Lr136u5e>?M!AqVw3@A8W`oPCC@Qh&^HUnQz_`J@?)4 z__L{T8mo(BgZ+1IrDl6Yo{T@zF|148i25}yZd&|AWYvMV2Ma1RL>ku~a4QU+pu})S z<*3>p4VK0wA67rmulRWXqC!#sR%We&jo%n@pLd&k+>vSiAU{F;z?rxHKhiX`udv?9 zOh{#&m7Arh(C#9u;@I5rxPU_BxsaJpp?Q}Rw?UKPg_qGKZ#mhwTJDsyw{7&7 z`YwIqdr43Ey7f)mG5JsTH<%au1muTZo-qR$v?3+05haeLB^mie42~&9nTdG{j=4#x zMd@|<;ZZ<&QINcIer|4RUJ0s#{!EVpKn1EG1u2OosaDBFsX&Us$iUD@*T7KM&@{x* v%*xQj%EV0Dz|hLT;L2RtZzvja^HVa@DsgLAdSIy+Py>UftDnm{r-UW|_GHh3 diff --git a/companion/src/images/library/10025.png b/companion/src/images/library/10025.png deleted file mode 100644 index 8a1562e528139134265c19ccba64fd0102526ac5..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 601 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxP?KOkzv*x2?hqn z3{Mxw5R22Tm;Jq&97PyDY_}=mP+HIW@RIq4+3bl+Rr+fi`R?s0`)b0>cF(GWyUET? zHoRqU)omoPh(em?2nKC4Bnq*isaXcFWx`P{>JGYnl79v!824Y zI&v{9&8zvRut5L4{Ri(;G8zwzb z^;1*f%T7~~lCpiS8##V`w6C#i+tqd86X(x@6}KMk^%g1%JymMyeeB`Ab9*c0u9PnL zsQLc)0$&}g#mii31E=noP+Ypev*no9%gXsPKXg3Xw9<5g!XvR6;^j}(jt8U~9e;l% zbNeA}&u<1M3UhMVXI?zG-tZ)gf8sVi4Uy8lZSG+gbuY9=c|S2bc%jW;=2?^0LZ(;y zdyQT+#IIU0Q>|cQ*$Mm4{=qK-*8jHyMubR-Yeb1-X-P(Y5rbn&QD$PEf@5w{YEgP! zes~m6UKAwnoS&PUnpc9Vpg+^&08oJ{NI^T_8W?Z-29Zxv`X9>mL6E@1=PUc>FVdQ&MBb@0H7@IYXATM diff --git a/companion/src/images/library/10026.png b/companion/src/images/library/10026.png index 704865b0c8afc2a54e24e170c2909ce53cf66608..1ad61712b6e8a8299f91366c0ab604e3294b09cf 100644 GIT binary patch delta 663 zcmV;I0%-l*1=R(R7#9ct0002@y&$6i0007FOGiWi|A&vvzmXvq5da5tNliru-U1j3 z9Xm*U`vH?p0waF{MM*?KRA}DqS<8~cAPlp1{QtkKJtX02zz~u>YGqA3q7z&j-1EEPLjG~0!fk#+rm z=Nl0!fztztqp!A`O&Te*a$s`gT8xyDG&%##)iPu|Wp%X^y5Wgrq+m}6k_cgkBITPg z^uksW7J7}_a)_|swVPGATCKj8-WFq;)d;g0Awz%P0$+6GrqXH(PwcY3bz4x&t)6KR zhNbP+rvpB-&U9WR@!Kz+2k;+iDK<`SR?2+2pT=nOc{$vf)MI^gqR x*!rHsG8KREmreTmk&nPf;3M!6_z3)W0>5Rp4TOcRLx2DP002ovPDHLkV1kTQFOvWO delta 669 zcmcc0dWUs_1ScZ{5d2!}bZMf#cs=85PZ!4!i_>=}pU=MHAaXq3Ls4#8+dS6C3twza z;1_LCnDA%z6l2_G%CJ5`p4b0z^T>E=1t-HxRT}TN^ECxww6tsJNJ3D zex})PeT$X}KU4O-uf0E8^1#xC$q}|sV%f8}{onRxzR zTVrX?B*MPIZnmK_o8@a+=F}zALW~T4Bq_0l);GyXTc*fwW7?x*|73xeSHc4uW2Fi0 zn>7D?89A_8ls--v8TK!|sgTTM>J| z=bM{1f9+n-@bK@=>aXq&CGUToWx4nEQrCW_uD8!E7|f0I%TIk=x!d=Fknx7UN8eT? z=5SPOV^Ed<_wDb@q{h?ct4g{4vwz^Pyr93q>Ej1JU=k21agC5HaV#y#$S-1WOexAt z%u{g8O-e0FugedQni#H}!=MUOQj(Hbl4_M)lnSI6j0_BobPWu34NXG~&8!SftW3p&>UvB{QuOw}zz$mU@8_qNl5$%Q~loCICd)ANl|Q diff --git a/companion/src/images/library/10027.png b/companion/src/images/library/10027.png index b872dd0b20759b37a59e522931afa876f281ab4b..bbf26657e6ca114c53121f51e24fc9c12866b04e 100644 GIT binary patch delta 820 zcmV-41IzrM2Jr@v7#9ct0002@y&$6i0007FOGiWi|A&vvzmXvq5da5tNliru-U1j3 z9vQYU=_Zqq0waF{;Ymb6RA}D4Sj(2hAP6Hp{{Js$7PX3qZ|`(5)81Oa5CRIy*#!|1 zy7v^p`}qDt`lJ3oXO`tN@ZM8IfbVyR@O#y~9y#_vS&i<%dZ7KlEeDvb>V;Fs0;NUV zMSv7!yh|4V$sB+vcr53@TNKnmNEB2d$nH=aG9FVw%!GfR@$3hSJUGvS9ErGS0LTzq zycJBi7y<_gr38uu8Xv0%$c&}r(NL+BUTUY+r%b<<>*Xgw8G+}d_x$xa1sG$y(5aIdqhXVu6;NtqmjWb;qWUGHiP-PJ!+z0_gtn%kpl)4=G)I9Bq zQKmZ$5X*o*M+CGfh};qMhUw`Jm5}v=>jAtkxq*OF^_>DUTD9#5Htn;MUZa6HuLac( zNBowtY}e|~!!iJb$PC+A3x((YG6D_zsQQhWGPSD%PE#dXW`b6{?b7*x_?Tv)Wtu3>gI%eN4iwBMl4?;HTpSt?Yw!XG%$ z(nj4CfxaRywPaIUK!2h3C@FmxPVHA+kZ-?vW*Uyc=WMc?O+kDLx6OBIWx-RdBY=sJ zpzO*9HIauQ;Be2_hGS!Uj@=>NSy%S#In{i*85b)Tu$~2r_F3(v+1j9T+WufD23>HK z0K9lgRvs7hQ?_xse#!p0THBG~rhN|EN&Kc9PuUm$(D1n#|9Ro!Y8KpBzfTqL|IEAE y{M^YxZjTNB6aKcN&(G8U@)^p2JDjK+VMfJV2Ko3Wq(0000|{* ze~eetxoP#kH~l|JQ>%n0Q)th~Dqc3gA2U$p5pH!H50t@`Vl_3N*<2{N(n+vVVInc^}j} z-~Vg>q9?zreO%Y?fAXg2iQT3TeN9$#ne)%6F?{mUtYSS8%4}eI;Xj#I-aI-~W+}>SykJ z5SZ=9De}tf;JPFWr=D|{g=F^dzI<(!$v10Ssg%;uw@gOI3bk(fZqa5aTUy;Sm+6W# zcM|jd7Db)8Lsohft*#@(gTl`tpTY@Oc4i%Z#A80?#H~kaA3&e{BJ4TiJhi)g@Q{Z4ujHdFHK5KT90v zHjfaqV26ZaNzt(1mUqsUPhK^txzcg^O6QeY?6SGhvp1#QZ9Uc(^T+Y-pIaL9nO2Eg!_oswy+CQ%)78&q Iol`;+0Du}vj~6ll`x{3zhG`2g%ug|B!zFhs9OXH!m;d zYwf?o6jJs+=hN5w4CYxm+>f3qIymdjS2j}Ql8ipCeBl$rTBUC%bE6n0ZL!x~(8qk^ z{gzFO_wp1hTlFjH_aFJ$_p_sd>XmYVX+xyMHKN3^v?L?Hh`}+XC^Ion!7(=}wJ5zV zKRgO3FA9=(&d<$F%_~7w(4XmX0H{C}q#z}+B-JXpC>2OC7#SEE=^7a78k&X}npqi| sSeck<8yH#{7+jev`wc}yZhlH;S|x4`OAjpd0%~CJboFyt=akR{0I(A{Q~&?~ diff --git a/companion/src/images/library/10029.png b/companion/src/images/library/10029.png deleted file mode 100644 index 8004650562e93ed77abfb96ca368c3416acbbc92..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 755 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxP?KOkzv*x2?hox zCQlc~5R22Xm-pvib`W9zkRGEdyJ}a?N|CDyZEF&>C%67!{^h=*#5qzxC{U)OL3NX$ z^r`^1f6Oxy6!;`}xlH-rkga>LX+mrJty6{l<#zXrMZB+l|8nu^&%6B$x7@c08b4%o zb_|f&E`5R{Az=_b|CqBDgoRBjoV@ z$(0)4FLyVO~3eAP|)E4W({#C*n%Wgz?(?rwB4*6^zCB?Z<5i6`3GWN#IhAJuLZr96Gg{+o7Vvx@ z>+JOsPLuVs0tDh_%r{G5Tc15aV8+4Oxj#1W)@N(z#2EfayZz?x2@{PfaZ`>D8B)A4 zY*95{liw`$HaYUewEv*#(YH72SdWYFXI1bmo7g({qtJoN?R%5c-!NEgsoN@jZ3DYQ zz3POHFo`Pd; zQfg6pU4D2JP+k-y@0_2To0?aGs-Qp9;{Z^BDo8;}Vo9o1a#1RfVlXl=G}1LN)HO5> xF*LI>G_f)<(>5@)GBCI@SN0oIKxm;OXk;vd$@?2>`8QG8q5> diff --git a/companion/src/images/library/10030.png b/companion/src/images/library/10030.png index 705741cea320628dee122dea76fcd88a37635b86..c109f03f172a19afce609b228eafb477665636ac 100644 GIT binary patch delta 710 zcmV;%0y+Ka1%n2V7#9ct0002@y&$6i0007FOGiWi|A&vvzmXvq5da5tNliru-U1j3 z1SufIBT6x3FZL>q+(&rj|`#C;Ho zpcgW1i9|rAB}oSr2M`e=pPC0E2tfiFC#rKrR3;MC;!A&Ci)Rqn>ri)da3Ns0j|lv< zThb!3oMb~Oi4t^^k^Rg-L|v(o=s_soS0WKm_^HhSt89J^9Trx@UmS*F?KNsAsBEIkAZU#%!Jgeh>8Lf1E+kMn zK~NY1*$033R6q@FIH-;7g)IWm?iW9`q||DN_b!ApMD&@Y4OjBB5hBB*te!yi6BIeps*$E>M*ce+90upT%@TLq%?f?w%~d2bHDZw&NM z(|RBfacM%rTQeFgHuV?_RJUtg_eL8Ard5~d{sHS#3zKwQioVnn=00jFpR=`7=@72~n}!ut&1 zmk4g$7lbhpHz08K0FXPez`Qf!T@~zeVExYMwh`_>{v8G2KOw;XtpaB&A^SDnQ2|%I s(kLB2QCq7DOc==TlwRx$UVHukC;$?kS{DxWMF0Q*07*qoM6N<$fR delta 683 zcmZo>d&N3If|HQ}2!5?~x-?N=yq@u=r;B5V#p%{7j@efnMA$!wrx~(teCf%xZFY3^ z$0Z%nyCkY!xqeVKQU4xPs3?B)ng;hh5&f&tADJt%^;-{}+mf)9``e{v+Yoo%x2a1P zFV5Sbc>biy?%ACkmOL}%RetXO-o`LZ?+1T@ws#ub%JHOr z?_R+!4Ilezk@|x_p5E*J{dVnpDXXpXXUv(mZhq~aPnOM7?x+nsX0K^m_fjJbCNPDl^~p#=+` z=WCflDr;U6G*EE^bLKB23_wpfLHV5``0ttkJ${T?fQ)}tSh4|r-n0*uGm=(nEK0b4 z9)uoIccBf493|4XCv*fk1V}7^d#+UxpehY;#Q;P^_+5lb-lHjsa0TJ927blJ@h8uE zgxKGnfl6pJZ>|UY+EEn>F9V1%?+3u9DtF3c8r?owtWuix>Gfx>M;M^rA5b`HiQoD_ zM5A;V8SQ_Mq*R1?XAnk?1uO?HC4L~g2t;{#?e%L85MlpdpLk&5#6Y&7UmUX5 z5|vB)=CV9~puOX#6yLJ7lUFYe?hZCTn4om*_1<~K@7!mr^%-sX@c7>6qpc5Lm-bHj zC-tlKz&1z40E->fZdwy8A{aM1#6(pvD7A5NaersHU&6hl`hm$W0Sn*saH(Q%^Eu1v zzkLu`YuVezKG$T;HptaIJ<*KM z?yYgxI}R=Wwakwnp0zv9c&kdykonCkx1?DI9rIJT&mK9bkos9d_QlFx$pdR1rhO6r z<8da1pUd6Q>c>NijF^1JnEZtXZ;u!9bh5MF|5wjAC*e@0PC>SD$s9F@OGlXxEnKX7 z)#&P--u23+t3U1LYxnb8bnoIq>xQ*?D;t?_temnhowZl+)N1$88Q-nnxh3?ZY22Sb z?N09j&1avzrt)x>tU9(h$8cd_&IH9GgU1h~V=hT?KcC3J@1^WMFZM&tS>Afyw&Dnb z-1LV+n_3el#7jh0DqRTvDb|%}Ht}-QrH|?-KEIsvI-t92QP9$#9okD(4eOnnK5Bk{ zF*LI>G_f)<(>5@)GBCI@SN0pw eNQ8#m{FKbJO57Tj9$4xHN=}}xelF{r5}E*Qf&}mY diff --git a/companion/src/images/library/10032.png b/companion/src/images/library/10032.png deleted file mode 100644 index 1ed9a3801cf5341d7f53bf302cd46d981f402b9f..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 600 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxPeS=2F54mYxgrS zFs6IDIEGl9UV3R`)?otywg=pdyPY>)<74BM+_kLarNEkv$#Dx+F04Dt?ZPMPrEc#e zx3o>H`it_B2^acGUj#UduHKenX~iFzCEzCi>F(b{3TK6dzcOtWxBQa8BjU*F@XNqO zfsswZiJ?z{EkT!KzSU;e+NQDxmYZJ(Y!6hJ^k5(3_U5~v%2;--Z+y9ww@%3CZUFzH z#)>DBjHMnS%q6Caj`Su;Z|Y~SQSyDpRl)uI{W%*Z>9TojX%CDeG#2drA<^Y@H1}b^ z`a5k+r?1C6%~wnp?ab|X-lP?>S6^>iJcJ;Q!)30ti8C0MAKwfmGz6l@d+y(`zI{h<-&f`jj3ttn?@6d|E#-otr@F= z?yx092p~Qjn5Zl4_M)lnSI6j0_BobPWu34NXG~&8!Sf stW3*}V}Y#Iw&eEgy-VYj3$ojtrt@i9oha~r zu+L%TZ{Kr`$}a9%`)T*@6eOjZ|Av9RX(KI(EiEt{qs@+>|e1+3fkD%*vl}5 z7O~f*?r%@~p{^}%PUoI8bze-sBz>K?@Y9C0 z3!n52^0U`m%3L>D>c_o<6|=4zI$u3>G-a0gM7A3HX@8Dg*uFuq#QwL;nHAq(?x|p2 z!B?`%@3i2DZOvJWCJDus$UWWaWsz~q{O2DhuD*@wQTY!`{^@4F35%McUN6GPdGXpo z#~{sFiqEq6j&+*7|MBB$+u}48i3-WSM+}QjdEA~{DA2jPXD55t)6jD>ZSI^n{guIE zoql;jrD=oOY4al|nF5}q&Drwd+_HmqW_1kF^Bq*x%nxXX_dG&EIqK)3#fs?)78&qol`;+ E0BQs*M*si- diff --git a/companion/src/images/library/10034.png b/companion/src/images/library/10034.png deleted file mode 100644 index cc8b37afbdd2e93d09354c1d2580760f280e9cbf..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 690 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxPeS=2F54mYxgrS zFdp=DaSX9I9eZhS-faT`_7B0KQ)F8Tt}bX=d_3h$!j$OUTh|LH^j}!&EVT2(g|&4o z`@3Q!P6%zuc4v~^b?HL@lWN7@#VV7!*iZjBxU1iuQ^G#%`0)jTZUxgnGFluiZ3$4# zP_3_ad=Pc@PK{JZO`zM3jJ!N|gRXpxNh~du;W8Refke8 z$63y9JK`N$|HU^g`0;Ni&%A}@&v{CM9p?LS%EYP%JipJWP7>2Uz4Koz7QC9x#cD!C{XNHG{07#iss80s3Dh8UVz8Jbv`m}wgrS{WEz inJfDZMMG|WN@iLmZVgKhEcF6vVDNPHb6Mw<&;$U>`w++g diff --git a/companion/src/images/library/10035.png b/companion/src/images/library/10035.png deleted file mode 100644 index 2e14bc9412025e17291c1ef01169c29af0d34e8e..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 721 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxPeS=2F54mYxgrS zFh1~faSX9I9eZhSk+7iv`v=jq04}z`T?H4ECm6XptaoL!G}e1@LfD{A$T)qL3EOs) z17`zv9GqjLr^Mf7w!1q0We@lK=jPYy{**R+`sgRO)%k_Oo+<1P1oc=aoiZ@{BU{>b z>y+bXc@r~d<$!P&L6NEoy#+fiG6ruwCh9C@m?JRv@cw1_O&65TY3G#QXL%_8$p6S! zp2DhwpAXBp)id4r{zX`;?R>?Jdx7q3k?D=!Z%=dgSkQJspy0Ykfk1)aj>+w<*Lm)h z8MGc{tN-GVtkU4xJzv5n;RDlpjwUe%U-w6~r@JdRTsa&Rc(lRc@g>fA%&g0j3nKct zuB30_ntIaV>&g~w0ShnH+hqcoQ=`1)3eGv~E|m9tlg;iW^vGwsYy-=omD~XdLL7Iw z*Il#qcqRCt_3gpLeYe-Kg)uLvf0gmEj6-eCV;yIO56M>~Gc0fK@qETI?f&Gm7X;4O z#fh%S3UeShhyIk#U<+R z%$n=HD{G6*KP#Km@SeOmn=zy3+*6xrOxG*QTlj6CSoR#)EgT^6Kh^5)+~Q+biU&P>;Qk0pPr{I{Ilv_j3Q~}gSdwa$ zT$Bo=7>o=IjdTqRbq!5J49%s Nc)I$ztaD0e0syqL7v diff --git a/companion/src/images/library/10036.png b/companion/src/images/library/10036.png index e4eb4667fd8dc359f30f93d9ff878cc38d180197..ec94b1a344098d2b189c4ac04a150c7dc79de829 100644 GIT binary patch delta 620 zcmV-y0+apB1*!#*7#9ct0002@y&$6i0007FOGiWi|A&vvzmXvq5da5tNliru-U1j3 z86Ia9>Ozw}0waF{8c9S!RA}DSnah^MAP7V$PyYXxYZje{FBA=$Ggf5%GMUBLTLHk^ZpXXiali-=V!J2=xPOI+uw#-e=GN?0 z6eu-7=Gz!fG&orU=+lpun4;U}gqT z3%g{vr*-P#P>Iw4wUA4ZPFobi60{=AB&@HfzDn$up)zj7zn*9mBS2B+9CMT_Yb@NO zYa2%2$TO9u27*R{XFb&z`_+c7PC&Z?wb-p4uo4CgT_DMUdJ~7dc-WUNYD7fa6lVON zW@+7woF9J*q(cDyAh`(RG>u+abF9jT0NMn_X$)&5P&e>et-3R)o>VaGBY?7b0kJW#MDuVjO) zm4Gzbm-yyPxW5nRe=uQF8KN`gSdek}VhI>`+y43R8Sn=?^UOm~;oOY?0000ZP#5f5MX$)k;yuGfvN1-S7#ry zO%dVmIpX>v!;&Frlb7R8-B=4RF|Ad5n*@)ViA>B;O0?-YzHxJZ`r5E_;^+P6NT_u^ z+nD~$(CTOUjGP=k4deGlXC!9nt8AWm=RV6q&I+&XiDau4VaIM=MKxvyT}1~;xyaUNhRKQF!{)QTx?$u0p>|cmyCudM*HoXi34M?< zK5>q5nbGM5%?(rcY8>ukDq(#w_shZTYiZj!AJua)3a?4!k#5~$%UvRQY*UN-@((*5 ztS36HeaxhF#Y)eNYb&2;-M({KsmlyPKS+A1ugJIU759EW$^P(hrk%lkf8?jA@E-`# z*lWkID&f(k$didhzqNUOe!Vi`lg&G>Lz@<5ANa+u`^-slL-o&F&qTu(zWi4GD4zRE z&);Wh-aEPU>NiaO^4K)u=c@ZBzFv+iQh0Eztnzt$ZSV$#1)+C68?874GwPSfNdGo{ zI^nf&HEYlAwaItqd9Hpi`R}wZQ$F7DT7JXf)fcX+S}|Tuy@Ln+b(d+am3gsC{^F0{ z2a33&`o8clZhh3JZmXOOjB=3@*N76w(vpn)A_m8lqRhlR1xL=@q|~DHy8Q5{iQ&pQ z45}a{DTyViR>?)FK#IZ0z|ct7z);uFG{n%%%Fx8h#7x`3(8|Ez%3RrRKr;~(`OLo80$UOt;AY$(9+U?b0uug4R_f*)|Xxyr?o+s&_BH=6IFDrPn{@of@cr-moQpoFbANIu*)As}U{T?%eLUWG-j`|C_b)b<0V{oCpLIEY)>*bxxA`XX(+R&9 zSg!tJrE1na7v?eV|M-0V@0Hh|YJGJuq7wopZvq`m_ zqh^7v$M&9@@A4<2ndCxV{%|_4a7R(#epBC~pX`A$l0W9L=C1}uy-0~`M2TZ*Nk)DV zgJVijW@4U#V{TGvQF>i|coa}x6eRDQpPQSSSAwdbKhxs?P=P8)K}upts#S7PDv)9@ zGB7mKH89jQGz~E{vobWXGBMLOFtjo-xH4Dv8;XY9{FKbJO57Tj9$4xH)WG2B>gTe~ HDWM4f;xQUG diff --git a/companion/src/images/library/10038.png b/companion/src/images/library/10038.png index 69425a5d3d12ffde39277763ee0f0897915f696d..71e3824f6f5100e1e329e13cc747d9344b1b1167 100644 GIT binary patch delta 514 zcmV+d0{#8`1;GT67#9ct0002@y&$6i0007FOGiWi|A&vvzmXvq5da5tNliru-U1j3 z2sQzEVW^XB0waF`u}MThRA}DqS;4NuAPmEZ|Nmw0u=Z`G86+fmNYgk?Ent(xE-Xn9L6i+g4)QdxjtZvU`eq1bn$%X3oI5b`$8R zP(`Sv#FhFNH7~mYnm{a*fGP!bGkzigltOMKfR`l=gOYzE!$JJ{KLntbN1_qwD5Ma8 z!6oW8{UMD2O#SLM{45`Ue%pu)0tWnN=bD0VD1#QCewxalCg7Wfgcl)gIzZi~zdS3( zULV+QMAlX}2jB}M@FVaeV0CU60l@FaEmrbIe7g4o*H4KZK4U*%ygsO5Kv=?GivWb5 z*6L%h3|D{gT?FV*A0lMv+Kk~?z{-~F#G~;Pa1GqSz(YWsU4J$3WRP++(-jU&LFl%8 zRHT28*dHO<;vzX;t&k0doC`2oEesKfJf3r~Mk)G-b$h;s?*X1V5;N`CzHq)$ delta 701 zcmX@e@`rVT1ScZ{5d2!}bZMf#cs&!hr;B5V#p&3~2lIpt1=t=$@|5z2ZaXe_E3cBd z?_t9qt;!Y|$5j#T4?C`?J5&lCuzkvOO4wn}w+q};W2;`c-Aegooo&rMt>}dM`-)@6 zYS&zj++8HKUv>i5|Ji|fqKZ+skBH@|&^M`79MK z4xhAnHi%f6)pMPU=2;?QVZvOcAD?hdsA5UH+?TS7DW(&q_-{O}yl64w%GE40>YNn6 z*6_Qua}-`~Pv)7>Um*L0DS76B0Kv8mhpw?mm>+rK&sicF^z^O5p_uU8it@F$n%%Re z`d`&6N#)Hy9l9#@;);`sUXwVd^)6EU%pLGb=+AD-$zq14AnVgDZ1ozX6RzXvob^$xN%n VtzqebrCy+f>gnp|vd$@?2>?%cE~o$i diff --git a/companion/src/images/library/10039.png b/companion/src/images/library/10039.png index 586fae0a569d4b3ce4f6110f7f07fe54aa244234..9715eb04c9634440faff222bd535f95ec27b0c31 100644 GIT binary patch delta 876 zcmV-y1C#vJ1@{J!7=H)?00018wCE@R000AXLP=Bz2ngHZPv8Im120KLK~#90?OWTD z!ypJXJNy5?oP9{wu_}mi5p2)H&UBk5aE_uNx$gT;?r~ig@@)tg9<+{JQLGQD0d95* zBtQb3acKXL^tX#0I)I?`&5z|%jMu;Q;|3ks;f=;~NPoLeM1KJ?uFKATDaPyDh87@c zYM{h;Wo>u?lAH!MjMoo6K!7x_!Nc`^-{Pdt@_C2=si#4^WzrbqOajjlApL7lu`E8! zWf_YkK+9uk{FVsLhhG7d2u&!bmiyY*6a5IF$9M@p{yzBK`*<7DGrX~%>;+KT_T|uF ztSBG4A!y4kJAYQ;T3!G?>3oxhHu#Z2CIoRvH|D|*^$#Rx07VAN;$=4}vw1ol!Xe1d zfeADkylLPl4-f&R%I3=DpWOzi0B7ITR`pB)T0En^{Od%9GX-daOs2a$Pxhd}nF0{; zXs}m?GZ$eTPzc&W#U~0tgbg#BtD&-}vJhr|Zj;lTFn!dsg*-ShQT82p$!&+hfIojjz9jfPYsk>td?)POwKq2x$3S!wL zQXYU0ja&g-raS0x>3Z_XF! z^?+_^qJNpI1#xPPkWJ;4(0h>GDCd9vQC7z}0ZJ|)qK8$K%B;Z)B=8w;p!FHSbTza) z9`kmE$Y%L5(Wa^a-AYH5I4z4=9EZy8#mniQYT#zxyyOS+OW-_!IQ+Y2<^Oae`<^2z z*Z{g7^vT2$fZ3CbD^Y&6s|vE*ST|A8TlP)qOn()LMbK9vmSTt;UL{X6T+o$pF2G=8 z!X(b1RvK~O)7c1cC=czmyk%sI`$>_vA&eKv?Tich8(;>sPzwFXl+qhv0s`#XBX(t2 z$R}_iwY>{D16s5+5obwvg}1CS9o`kO9IVWyb!-7Bc``+V?j3A2h%JBtv}4gBYd{O= zpk-oeT;~@Ez(NAMR2929m*~ILDAp+19yysx)n#hkH)zp|EMPY1iXl=Ok9w-#S0j@Ps+{)w(Ac_gP-Xn^s-8o88b` zKTTpmmU>^p-NhUY72=2QmNaaQH(bP+_hPlY{eipI=86sb{qMF2p6kwQ=8Flx+mmpN zdBJXF1*QkqkJ1^Y{l3H!T;Y0Dt9rvf2Q!I(18KT5C7f zvFt8qjOpAWnD5jf;pf~@*?V0pqFJJ*#!bWYTS`IS6z6rv1jOV#cmlfor4FTOb?kBr z(XW+Sx4X+RL{EtQ_P(G;Z|^u?eXdx!|NTNky?niX&zdC?Jrnl@6in*k{-?6r;r273 z{XyH;dIweV%+b^lHfLfl+-S`1$LSq!z&_*RVa^ZN4pr=kxxZe{?s3H5WAYCl>^AXU z^rCr}$o7H{z8AF?ii>~JxK;6E(Tc1WKObIwcy4D|z=x%mr_Ou&Ira&km));zNhjtd zyk1adT6*mG>2DU*vKP9XXPi}%-&p^*f1>ST!5CS+VKdAc7@Aobnpl~bX&V??85mrdEBg&aLvDUbW?Cg~4NDI! R^#W>O@O1TaS?83{1OQdcC@}y4 diff --git a/companion/src/images/library/10040.png b/companion/src/images/library/10040.png deleted file mode 100644 index a6f575c6f1efd42f490924d207269975bf39fe07..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 450 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxP?KOkzv*x383Ib zPZ!4!i_>o}ZR9;P|MipZw)mRDEPF4wpOEbF+C0cV1aHKE?1x8jI(EsB=&xw?{MwB>~mSp4?F*v3aWhUk+IOZm$7NytaherYB zMM3h;`MJ5Nc_pX{`ZGNa02Qc$6r?1Uq*^5xr2;7iBLhPtT?0d1L(>pLGb=+AD-$zq n14AnVgDZ1ozoBTz%}>cptHiBg>4BwQKn)C@u6{1-oD!M<$F82d diff --git a/companion/src/images/library/10041.png b/companion/src/images/library/10041.png deleted file mode 100644 index d7c5094495ecd11b129e89b9963ec13dae8c3585..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 819 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxP?KOkzv*x2?hox zCr=m05R22XSI%dNI0~?Rm^IfyzNIA3kty@O!abXp9CjV|_N=PlP`M!7R3Z3C`pEJR z8B(^DpI+rwcP`lOW7fFkWKMnERpXP#bWR)m*|uxdulrm-UdrUzE$R=r-x&7izd{jz z$2Yb~9LKkO@p98Hsh^RJ60 zvYkme_v@g0+N-D58`O;j%^fCj_j_5aync}V+gz2OaR=wJ+}8>@x!mg)SNOwTza^`; z*T#2;@hh!PTI%PUzV4vWF%|LL#%WVUtfc2W+2tZ5l$(A#d&RmE31bswi8G>EOl}W? zb|10i_G#37mbf?Fob{2E{PRau-?VSCh;QfIFSjG6;pC&dwU$yZiiCXLWXH~mp5Xp~ zkHdKPi_-%A*F-90`rSCTF(_%VnmrN8Iy6sC`hja>T7!+-i#|7&carV3S_dB5+3A0n z;<>f;g>}O0cFa7*n>vjC^8-8N6E1GpE z+wefrsjQ3K`HbeR?=P@fuWvsm79o=;AG7X7cn@d6lEsnDLCdPr52^v<%dTBlW4geLXf)u1AmZVxG z7o`Fz1|tJQBV7YST|?6lLo+Kw6Dt!lZ39Cq1A{AbWxt_l$jwj5OsmALVd;UTUO){D Mp00i_>zopr0Jlj|ssI20 diff --git a/companion/src/images/library/10042.png b/companion/src/images/library/10042.png deleted file mode 100644 index 6f4aa2b6863b57c685a458f430705e0d56885ab7..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 695 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxP?KOkzv*x2?hqn zW1cRKAr_}wFCWaiZNS42uu5vtX@R#hoD<&~S7|Kz>s_DJt{A3&I{i)XvqJ~INhUww zm*|#T#x%>~(pur$?N>XPf8Si>;l=h$zA>Hs#CiRNO|ecpn?&z8PU&tpezMz;!|JCp ztJFTJo$pM7p0mic+a2A{v&!?KiA{n<=!FYL5f5I5{HbNkP;FK)uu071X*?79gyo&Q zX1&RexOr)3qZuc^{bnSmYLHTKjzLfMKyNVfLA}Grny0C3)^cdPeJsq=B{)oBa{gTo z$7Z?9>i+Zhiqu}vVijO|IzhK);vJDsY6`BK3XIdvAK%5Vo^x>-|1;JfyTxC`n12g; zIQ_kKo8*S~@3k#hzH`;zT72@oP4C)}A7|aQ%a>Gg{&|xBM)zHf+;07+*H1*x&U3oB zM`X$O+q@Sfw{Y@Ga9tLNTv)~1cSuA;`MTRPj>}uluMsfx>pU6AyhUQS6)VsK0;%1q2taLi3gElRJ;503)M zi-P2x^K)}k^GZ+^^k;e;04h)gDM(2yNwrEYN(E93Mh1pPx(0^2hNdBgW>$tKRwicJ o28LD!23O|FenZiao1c=IR*74~(gRDqfEpM)UHx3vIVCg!0E{mfEdT%j diff --git a/companion/src/images/library/10043.png b/companion/src/images/library/10043.png deleted file mode 100644 index 7ff6f4bc7c99089aae6ddd1e5a7a6b3003d450b9..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 638 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxP?KOkzv*x2?hqn zUQZXt5R21CFB|5`81k?NaPjDrYfV1o(;#zTX}9Z?#ZNfw98F@^9lhh?97gFKmY!{XL}J z?gTG#>kpJ+n814K8G9M+-A!Bae0x_^Rm7ZW>47WdwpIq zJLy(a_ty1sUi_~b)_#A!BSF{t!>0Wo+LYtnV-BsVz93vz@wK_N$|=r3veJIxjVFTQ z6&Gq2oVz1zmD!wO6cRjPpZ1lOYbz>0aOy_&M%`PWtmt|A$!o2q;z=^w7S=j1eBmTi zQ@py_L#=lC{WrIl@2VEq-uZUXja}6NoJ)0=nXi~4vnto&xLw+nOaH2-+2bOvPH86O(`njxgN@xNACtUwR diff --git a/companion/src/images/library/10044.png b/companion/src/images/library/10044.png deleted file mode 100644 index 0f5ec33dca432c9f1dc1d4c8fcc486daf65f820a..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 602 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxP?KOkzv*x2?hqn zOivfb5R21WFWUPZHV|PeaF?`k%i-xLZ{1|5P$SxR;6#Xc>5CiMqNNE>xYkuMDzn9$ z{PDP2Pt;SYlaqhj*Wy3Vs|_u--Yqn6h*m$!@tb+!45g*6M$-g1Z=O*#x&*pd^#t# z{D8WqK}vLE=|+#5Js)#F+Hx4*Pig(ixhOtm?aNh74=jKA{%T!!(`mx+wJ_)aqSPu1(FBKn9eXv3x06?!LJQY zJEz!1IGHzD-)`soxlgt++wFn)JMpeVZf*j%Uts3^SX+f96Ay2~ztQ6(4#Bd)#C-1jd9&iEBiOV`)i7ei4IXN>OHFo`Pd;Qfg6p zU4D2JP+k-y@0_2To0?aGs-Qp9;{Z^BDo8;}Vo9o1a#1RfVlXl=G}1LN)HO5>F*LI> tG_f)<(>5@)GBCI@SN0oIKxm;OXk;vd$@?2>=4b<$C}C diff --git a/companion/src/images/library/10045.png b/companion/src/images/library/10045.png deleted file mode 100644 index 4e195cbb47a8feb6cc5bfa90fc0308bbfafab673..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 762 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 diff --git a/companion/src/images/library/10050.png b/companion/src/images/library/10050.png deleted file mode 100644 index 13f2c3748d2cb6f361365dfed7f2fe32fac71bf2..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 701 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxP?KOkzv*x2?hqn zGoCJvAr_}oFFAH!b`W8BAg(6CuevjnuTh5O{6{5S5v@1!kw>!?T_?zSsRtdLeEYCm zSYqP)-QNWh4X29kUKEjE%`wX%u{x?pA#bVYyyR_5@;4Pr{-}6=w%VAvV(Yv$+DyOZF{wdbH6hL(AutVB_%$+e4uVw|6H7YSf%h5!tlt`UQ~H^1@Aq5Bt{(PYPnNzpj34 zMHA15DXM*L%Syi|&OD^%dVA+-1C7<|v~BNg5;(9n;Sx7rN=u;Qr$3D6t(IJ#`cL4p zou}p(>mPO+)$#JHcW1EneEE1V_E)Fl1M_q0xkhVa&TVs)_xdN%uHA6_)ajEP*=v}t z?K_;d*3tV{np@%&tL-&=GbeRp?t>5b6fb9&!10;loZF_tp?Wwv82!~dQv z-hV6kmamZOj^A-fqOWet>T8dSEOKT=#vR(dV^)mQF~=j8jiDS#zp`#b^|+?r`DYp{ z!)ei@S0q>{*u6s9?e}-pJ!g)dY-HJOZOwWA(DxOyyMHWixq38J#%}5cRdP`(kYX@0Ff`INFw`|P4KXyc uGBmL=G1E3Mv@$TbGFSE+iiX_$l+3hB+!~f1Sn37Tz~JfX=d#Wzp$P!5$sS1n diff --git a/companion/src/images/library/10051.png b/companion/src/images/library/10051.png deleted file mode 100644 index 00ef00a9e28eaae055566428fa6a1bfd662eb4a3..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 678 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxRpVe@%FN{ZVU{J zTRmMILo80WUOKPMQYgak;r*AnJzL)1xnVT3xkzq%X!Pno%3)du&PM90yt=1DHcG;#m_xs+$4|?~1eYy90-}UdOADFvksc*QiEYa7H z|BumeVb&`Vo8YAnBy6~ZT7ygu8|~;wd%^OnS54G8L8`Ftpud!1r-PDYvc#&5Cs`Qv z`8b0fX+HQU8FR?_F~>QPj6P$Q_ACYU85svcZps@(>|*rUqi?xFC1H`$^eHj2HEiy8 zE~;!Ae!f`xg}R3YJZcw)*r)J3JlRto*v>UoyX*|&sjN3 z!7{l}-uc|+sLemD9V$0oYIdBXf2Y(vv2j|=KHW#l?wouz-9ov1Vy?1+U&A+nX`G6S2Nyki4~a z%ZCpc@oVKpwjE!8wES4`!-qHjZLxQ1NV;*j_GZq``Cp8G{`r@)`N#iT`h1MxI+59Z z4}q~NQsNp>;#gXekzd5%m{OFPn5W>Fo0M9VUY8#p1(X*B$vfxg=BDPApepFk^f&-i zpbAoul30>zm0Xkxq!^4042^UR40R1nLk!KV3{9*|%(M**tqcsV%$5Cyq9HdwB{QuO Ww}zz$mU;m-FnGH9xvX>$GMAe>K{W#i-kN2xinB@_8tMMPy|Wo7P&loSLCOymxEx$J=& z$G--pS4&8*0ilUkeV?=jZxu1vvb2g zezV3T1Lfn>j&673IC*E%Z;^?rVj`yOO6*6QqNg*?+}C`vNzrnl4)gQPUm8#7lqA-P zsx0GWTGwBH_>^njTdh8`gYPO%luXxo>HT@Tm947ZCkKz626z73lvg@`)}3FZ#CTtF zd-3%0kj?R;QBADn{Cf@V7dBQJU1{ek`IUNdSqIyeU-7$aL=N71cq%LU{N#PpFRyD? z-7W4?VYwzu{Ive@2&o0%xfE>VOMTP7w1K1iJZ;q0*-MFufm2KybnliwU@NjUPNt^U@sg0{8|Ur#hfX7ahs zU`-7&V3}DJ@RR$(6!9CjDm*#2Sk5IHX&?XBd|Y9MJ@Y%qm2!XnU*noApm9?0zu#+v zTLmZM?=H1&TpXly9~i?TC9V-Aj-@3T`9%zlDMguyc?yoXNvTEYb@|~@KzUJ+ymNkT zZfaf$s)GJZj{`sjsvrd^i6yC4$wjF^iowXh&`8(7P}k5j#L&#j(8S8bOxwWF%D~{t hT-k3Z8glbfGSez?Ygl?GAr_~fUb6K&Y#_q$Ks@zB(-UTcA6!$JQW+k$${h?A6?ip=*IY-1U7>^5u(;Rb zgp#|1YHCN2rZSIXq?Lo5XNGUGUI1tR{Co57887&lkiC#k@M^=VRZ#~g&2$i`3@uFO zU7E_&Vo|WdYLV0oM#jt_i+{_mOk-qhIpyiFUAMpSdn5DP-Z-NT{~N?*`_7vNY-pX+ zY0PWQ+w<*c1oIZbpdC^|_0b8(g}*T$TX<{j_XT^sYl`bl&%a99KEo)&?6u&f|6X^0ebk-I zG5_qGM=AOi1+Uv*=bYL-$!Xb(a>2TLjq1-IrhfeR#jf+mwVKoadGD`mD0$O&V(mL% z0E(2jMwB>~mSp4?F*v3aWhUk+IOZm$7NytaherYBMM3h;`MJ5Nc_pX{`ZGNa02Qc$ z6r?1Uq*^5xr2;7iBLhPtT?0d1L(>pLGb=+AD-$zq14AnVgDZ1ozoBTz%}>cptHiBg T>4BwQKn)C@u6{1-oD!M#-j}2`ab_iMdsPVjz zaS~@VKg_cAU02(&o?t_Lk&AP0ir5{h)~^q`k!O1IS-1WQVJ>b_;S6O-K?5E}hC+@l z8O$k)BAxtP9?JYNoCn&|c+WITNwV7nbcix?iZRJdv2Xar>v7ABUA_6_oR4}Fct0@u zt~siq#3(6~FPKrV&0A=7;0lI2FEw|B{^7J!{+c~Q=F77)j7_^kYXw>l)J#w;;9*K= zV_GDq5Gx>U#r|lToz=XEUoTRUDm~TCuGzw9Bb2dg$C~f^YYx{~#=O|#<6dlN>&qRn z@aU5O?po8`Gv8)!e_Zr_MU-vl@7KGtsy+p*E4K+>E&fsOp3IGzs~5(rTc0jAmg&#e z-*$SQ-hXC025nxQnQ6Os$pXVvq{KC%#Idv_Bfp5jF{LOoF;BrUHz~C!y)HjI3MelM zl6TI}%}vcKK~>P7>2Uz4Koz7QC9x#cD!C{XNHG{07#iss80s3Dh8UVz8Jbv`m}wgr mS{WEznJfDZMMG|WN@iLmZVgKhEcF6vVDNPHb6Mw<&;$VFaKQ2a diff --git a/companion/src/images/library/10055.png b/companion/src/images/library/10055.png deleted file mode 100644 index 52ae8827b98a8ab2c6e3918ea79e69ee10a36db1..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 659 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxQ#)Wanh!}Jq!$t zi#%N%Lo808y=?1s#6g7p!+#4`mm?8edb7{+isk4Wi8;ErAtF*EN2#gz_y>k0)ipV0 zyBEnhbuS6x$vUEzG2`RjlyGCmBbQ7X<&EEK>tERXd_mPi?gXcc?fDLS7|%Ck?BvXd zQ8Z{~6Y!l7DJ!C&w4P0bX@&EF2UoboEEDRPTVF^AFuYaMVZ5fl;2%?W+AYg7(ygM! z5i|K%1kDnk3z=;6*z>ZQC8Aw4`bCqJ*B8~VS6X}4BydZ;n0ld+V@;ug##HZw*AeOy zxSVdXHZK-tdKIVfocoxKoTs`KOYRP@kOL1@m_rXPuv~a_LZnTQW9gX#Gd~DQ*)p^C zel=}gulYjJ`Ow?x2ENv;>zQV+U-8QNY2MB5*(VpZtP*F_ikTMQwwrf_0h4;tgG!f( zV57x_7pE2_J@xTkp&!d;Z#1n>!EBmd`?;Q_+6#(T^Lf2El-Ka7$JRFIpXx5Q$?f-i zZ+(iko?Niw{-*_pP4?XIJN%`j#4c-j$)l9g@(({m?#+wkZ>ui1n_nSkv#&+|p>?BN zV9%GYNe>ssf9dO6*Z2Id{H8zrKUi#h_i9g^-LMQ8g(4-c5haeLB^mie42~&9nTdG{ zj=4#xMd@|<;ZZ<&QINcIer|4RUJ0s#{!EVpKn1EG1u2OosaDBFsX&Us$iUD@*T7KM z&@{x*%*xQj%EV0Dz|hLT;L2RtZzvja^HVa@DsgLAdSIy+Py>UftDnm{r-UW|A7%d- diff --git a/companion/src/images/library/10056.png b/companion/src/images/library/10056.png deleted file mode 100644 index 7c9be6730a951510ac677606cdb191d40bc0ba49..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 563 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxQ#)Wanh!}Jq!$t zPM$7~Ar_~fUf$?;*g$~o!TqlZY%P*AXFcQ9+GwEgN$Z1BZ(#fx*3Rc1YGK|wk~;F` zeo=3DI_Bz4v^)BIw|)49pWm(Q3mC5m@W0TOkh>WAApd&9Rl&AhE1IL4`BYULey(HC zW1RAUW!9!dQ^s%XJB}=D;>fvPz&s;f;VWut5#vBzVH#8SLdm<8l)hI$Lqs1@aq+4T~8{53NrO%kuJKaA^ zTes=nT9P)QD5_z%fWpoT94yKcwcb7EIXipLp^MxF7aQ$Zsva$JZwx$kenZS|2lM8s z%9;QCf@h~^Hup(Bi)7hRICp=K&+8qAZO6DhPE&Dq~%_`rDTs|E6ECZ_U4T{Aw!8@84g6K`c_@8d2g{T9T1p#Ne1x zl$n^P;Fz0~T9jUwA07pi7X`^X=jZ08=9Qo-=+E>x092p~Qjn5Zl4_M)lnSI6j0_Bo zbPWu34NXG~&8!SftW3zQ{H81^|ocwnw($&h&JV6K|F*N2^&hhqhF zm}V4gJ}>w`!brTJ*|%o1zqW<40MDP*SMMB=sp#0B>coBLS6%hlET5+ZRkI9M+CTlZ z_SlRC{ss++e+`pXz6>y0ppYyfW!1HNnX-1)g;NXiFDR`_YujeFMn|^oL z2hGwwsQTfk^pW@H`5vk=zGY?1ZLNK8P#pbsmww#kPv!lWD$NZV%?>Ked{9mn9~x-JSnI zAWQN0!}p3Al-cgzw7=ZdDzPKj>U!LhUt9gDmrz~iT%)NXhbz`j zmU35kq475R;7vD!&B0ZZ{o-TAt#$=<-AWTKdAc x7@Aobnpl~bX&V??85mrdEBg&aLvDUbW?Cg~4NDI!^#W>O@O1TaS?83{1OTIQUPAx? diff --git a/companion/src/images/library/10059.png b/companion/src/images/library/10059.png deleted file mode 100644 index 3d5e9bfc037814bf9ed05988adc097b2e45b4ebb..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 703 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxPeS=2F54mYxgrS zFrM>taSX9I-FkUr-faT`h6}<-x@hA=7Fm%?jIR|RyKLRi zaQf_+`>@re|6HN7eIs7ldcGrO$&bG~KWE7H#Y zI?R!DG@zKh!hELfGQ&?*x{vtmY|jZlIlG6|Jo~Iqzp!MuoCy2vO1lGB92|d7X7_QF zu;ANZR*?VTL1L!DWOr7%2gi6$_j4RN9CS(4UeSPGL;9E>tIFMNf?j7o1+x{hZ)}XM zW8$B(c;~WwE`?VQ8bVG^uVT3TOx}sv;DCS7YC)UJ`a#ZpEs^fd7|G?3|+t_P4>tpY{tNwA_>E_}0VsTX&*TeSmeqwrKFXSZTwC*v3LAaub zr(mqpjEP5GBTTvt?wD2bOvPH86O(`njxgN@xNAlV=dR diff --git a/companion/src/images/library/10060.png b/companion/src/images/library/10060.png deleted file mode 100644 index 2837c53984c42c26952edd24cd4c035656ad3bf3..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 1567 zcmZ{kdpy&77{|Y}8P-g#%c#r}MQgQnkV|P}bEh3Gx#cqEa#-6-Ki5u-5Su1C!spXc*>p3nR9?~}@OvQ|ZHL;(O)ZEfhzau>)& zRhAF1&`7u}HwCu6H65&+PVcxU-&FWEZpQ&Y&HfV1qRb#007Zf=oyH0pZgdmXju4a+ zmsh-Z9V_04Y#FXy$hZ~A3rRya3tD=!v(iQkd8yE?lxqcz=G7ry=}h;O&-%eG>T`Nm zMxK00|2UOE*skPL`yhk1iU#9H^*f6C0MmB&wl(=_Ass5gJ>Oa|vSdb;_BWOm#0)B2 zI02(2a=YG6;foP%K#wAj;Yaq>Ej>gY!LYPj?z~LwPbLhakVB4fb{6*JXp=lPp-HOB zY@f>n(xE7XN$nWrY~A;PoHMo?Zii@$g+gd%ys{tql)ZvykOqwLz`TB$!h0Du0t99N zO)z>5*%)ZM>6&w*wbaDqU0L&B^x3ZI5AsK2noTDUH3OS-3F4$>g2JB}y{mM(4EfLTBT>paZ}62~2EA^@vA0 zuU$_L$_v{~YF%v%ue#{5_Y2z!T}~_wv8`Y)4wT?-P6PTzs&d%Fr4|;(qW;QU@Vb%~ zmsRQ!S1!OXNMlv!l>JIYqgs-Zx==@9$0zr)7+}Z8*FT%n%sy0{#c=$#kDz`jlZEhy z!lhpiqoqS%6cO^vTdd_jF2bzh1Wp~*f z)cH}8R*s22&tJYQH3Dz!`YU_gpRQIO_GDR1878>1Ld&@!>VDHikE5$l{?7%7kM(+t zcjeqF_9&q%{ec6w;HEx#E3w;%D}pBZ2`X?x5)kKGf~K}ps@*>NWnSkwr1`5Oz4>F7vR(!K(X{g zfu*yHJ)SjLnL`b=&k^c+U4oFdHjK#4SY# z$?y2ICB}wQPkV<6N>AXWlRc65th#S8LM9_^LjiKAo6hlkMVDRWUr*{H^k#SAA^|l? zSco)(V;Hwjw$@BsgPAH7DawizVLNZ@62Wx(xHA?r_nZ`gd-J2?=K+1;9ehJZvv~LL zXPc^zlkG~VhZmC(-k-M)H*`0g1HU$CxQXl&U>!`*3bPSH!gpm>mY_JL<@(4cwvC% z9~SI;j6mbEIbngZyd&=NeEqN7lE>w8jzPZz>A^NqIiULs@b`r{rhZ`@xq&@o${rG# yLZTS5C`P6f15*PdBAH@JCifR;e*LY$<@pB(ME`$5B9++53&57)M6a;$N%#-Cd$NQ8 diff --git a/companion/src/images/library/10061.png b/companion/src/images/library/10061.png deleted file mode 100644 index 2aec8a70335e5e7cd88e722382763eb8f21866a7..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 732 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxP?KOkzv*x2?hqn z*PbqpAr_}oFP+W1Vj#fqz;myX$C_)`ZP&bVR^9RJ2J@=$N45cuHV#^Px~mEVI-WMn zG8W2;W0~k6cw6`juZQQ+Z(+?<9xKe7AOG!?t?~Sld2HTB_JWP`^!9Uf`|rKZDEg26 zP^(dj-iZmjCa^Ezp2r<&uEf>x!p(ratU3Bhn-ve+5w@+eUu@aiZr5&D_{Lt|N`c*? zBxp(hB%e1Ti+UqIoIQSw5w&-1>DZjx&A`a|n4~q`j2wI&lg+%McOddXC7So&8_rl^5n?BJaS!{F%!5h8TP6hmogl$;bNV(EH;Ib7Oj18iCANvm75i*h!9Sr^tibo#hr%=GUmQIqb7?-4m;e5p zBSrWBytp)*`9uULKNd9NzNpH13*{sVv2 zRlc4ZI-+xcX+fmKHKN3^v?L?Hh`}+XC^Ion!7(=}wJ5zVKRgO3FA9=(&d<$F%_~7w z(4XmX0H{C}q#z}+B-JXpC>2OC7#SEE=^7a78k&X}npqi|Seck<8yH#{7+jev`wc}y cZhlH;S|x4`OAjpd0%~CJboFyt=akR{00!JG%m4rY diff --git a/companion/src/images/library/10062.png b/companion/src/images/library/10062.png deleted file mode 100644 index 810efb9a9e55a84a0da15a039625165a9ae38a82..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 647 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxP?KOkzv*x2?hqn zX`U{QAr`04Ub6Q->>$GMVYPUV^T~&cWWDkQ<}k-b>4X#%e3AC}`xWplV}uXu`6ZbrRynxfC*5#9do`M~g(Ysq z^z#ccf69Jjja-tl&Ro;t@~Xn6k7e0fKCs-`b-7pR3(KC|pbnc#F-( z^76gM$)&nFzbrM$-9y|ewIxS#JxT*YTZ?CRdjes>3xnpn>$}i z``Xw!yt4Zz{fA+rM|668z^Wg>XcH-MjVN&}Ey>6)VsK0;%1q2taLi3gElRJ;503)M zi-P2x^K)}k^GZ+^^k;e;04h)gDM(2yNwrEYN(E93Mh1pPx(0^2hNdBgW>$tKRwicJ o28LD!23O|FenZiao1c=IR*74~(gRDqfEpM)UHx3vIVCg!0GtZ^CIA2c diff --git a/companion/src/images/library/10063.png b/companion/src/images/library/10063.png deleted file mode 100644 index 2cd293505713c9bbff457802efbab26b4e094479..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 543 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxP?KOkzv*x2?hp6 zJx>?M5R21yFWLIBD2lLuuwS?!#oO2C1IM%ZzDXo)eLCsJhC-wB>}Mu4 zn%?p@^r@4q_-yA;TD#Ud@$P!%CH9K91eY=HkvniwPHaIti;t|!fszM|R~wmA*cpz< zS)34CmiM_oV6$UGqnG5e2JPBIj~R``K2$8^x47ddV!-FmbAYi%k9oh5#yVe}1y?6I z1}_mUX}+*;15eEa=Z`@@ttKXli55A`R6NPGuW_A#RzS}-rjJYWS$8DFG$`jLN~$={ z(^^sFQn>t_iF}rxr-4gxnW}i58jJ7AxPVPx|0GLxNEF#Jz4L6jv$R`VRJ%3Bqb&Z( z3QeE)wicV)mw3LuUK^iMWp`^|VE?=8_wJSaFSFZoXytsvjbDt-@-JUtE8o4@QNn%q z+IrsmyBryxxHoS63=B?@64!_l$I_CF{2~U&l%mYUJO#(xq|~DHy8Q4cpu8wZ-Z?)v zH#M&WRY8BI#{r-MRgi*|#FA92j@=Ix`|7%Ci|iZ{Yjw&FCDrFQ|J9$dh&Pg3>uOWb5d-$5 z4Gvb2)y>4cAAC zx`k&La+=RuJ_u(!xz$i^${g!}lnlmIjCX4S4L&&X9rfPzT8MqKN&~lsOoZTqEC<#L zj3;I&F??LQm0eFle1ZSz4LnT>^O!yAU5b_;Gr7&T^G3_TC66yXKjhE7_Jo-5j~wlP zhU_jp>*S=Wr(|4T>iJUp8TZMA?yE}Du2$8Z3w^>5Y6WF&xh0isnzp@2xAX zueHC>r(6Q&UpEF)B-lM>F{V!W7LlE5J>z1JzAeO;f` z713k;&+ji0R9_JMNwco5o;Bvr1O5+LKU-rCsoC?hmc6{&c%r}~;fUQ~L&x=}1ZOW; z=@`4`*k&#}7U$E;eImOo8~Y-+2=gd<=&KvZ_^$}x)Re6u?htpd`PVnzeb=+4b!HN z>pxn5=MV)3y-0~`M2TZ*Nk)DVgJVijW@4U#V{TGvQF>i|coa}x6eRDQpPQSSSAwdb zKhxs?P=P8)K}upts#S7PDv)9@GB7mKH89jQGz~E{vobWXGBMLOFtjo-xH4Dv8;XY9 b{FKbJO57Tj9$4xH)WG2B>gTe~DWM4f9QEMf diff --git a/companion/src/images/library/10066.png b/companion/src/images/library/10066.png deleted file mode 100644 index db4917113f965ac24f3cfc922f79c41d209bcedf..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 658 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxP?KOkzv*x2?hqn zg`O^sAr_~XUOt$`WGKLJAu>#>^-$bv&A%-9drkj}EVO?R=r6rLp?<*yf5Ul80zL@e z2`lKo`{-b-N4b^p>{!!wr_2c&{V7J1dm8RqY>Q85H|XBX{ODBk&ZfdCZw2Pt9$;XQ zn6-uV>7^Y>4zh}DW=^xBLDZ)i1#)~6 zLgz{hSWj&c>DVb|H7#o+567p8i7DqU%L&b#`)=V{o>2a}6h#q58K)J_2jU+{IGqhH zJyr6u=1}dj-k4vznvd;26wZFXLtkhKGuO_EMZqtEmKjxKbF8oxk-R-ksq%!Q?33fy znj3dadwy@rg@FDutai}_oX?cwri;m$-MI6?n9sH#OiVV{W}d?Ft_S~EM8m%LeB_i7 zk16}`j8U22ELCFpj;5j|y`f>BdGBPdQrv&-!-_RY488IJdtS9$KI_Wsm*OjzRf*Xb z7;)g=t@Rbtmqj10I}*SZ(Y8qJLZ8(HvosdLSXa&o94ai_!Nsvt(q@{h%0IpE&g9GD ze=oXJR^2rC!oQ$tKRwicJ28LD!23O|FenZiao1c=IR*74~(gRDqfEpM)UHx3vIVCg!04sw5 AUH||9 diff --git a/companion/src/images/library/10067.png b/companion/src/images/library/10067.png deleted file mode 100644 index f188c03a8f05ba1372ac8c7b8cdbecd783cb6aa4..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 524 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxP?KOkzv*x2?hp6 zX-^l&5R21$FB#??HsE0mV3o7^#dbEZWZ65$7l)jW%PEEnUQk@zA0WE7fm`28al%ra znTv!zS)wpr(6uu(~|WaTXBh|XnfG8bqXxrTNG4fYFh)Uzs=>pSQ_2JdBE(#=z~u%96b=eF4)phV?Ta_#T|JKwaR&feU|m zEBJ5A2%EO9HF=!7bj7A4Yrm-3E$3b3s93v?>kLoK_w5J7*LO45zH8v#BT)V&)@{xu zH%sfQo_8nsCFwuZtF)j0t?ogw9p|OXMI0~PA1v;v_^`3Y<`2^&qh&?T?7Hm0uoEe9 zjVN&}Ey>6)VsK0;%1q2taLi3gElRJ;503)Mi-P2x^K)}k^GZ+^^k;e;04h)gDM(2y zNwrEYN(E93Mh1pPx(0^2hNdBgW>$tKRwicJ28LD!23O|FenZiao1c=IR*74~(gRDq QfEpM)UHx3vIVCg!02UR*t^fc4 diff --git a/companion/src/images/library/10068.png b/companion/src/images/library/10068.png deleted file mode 100644 index b70eb70d785190d60751b33e670950421fcc538f..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 560 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxRpVe@%FN{ZVU{J z_MR?|Ar`04Ub4lhX9oqVAoz^{Co4js;lJoAXZeo(5 zU#3^xSk}Ymx}1$qseWR{ES1FX3%?YzoMW|NQ0Lso9K!hL>d}ewA9$WtmU*yI>_OCn zc`P^B43@B5VVuRwbJ(Mumn|-O5$}qwg;$x(7;mw5JmYxIq8u1|<*?w(O%BaB6yn~A zC%lsVVpw)=OW#cs?jFV9_@m1MZ=Km4`+7CcyabaqPV*05l_=dYL-|AfH0F;=&Jj$( zS{@9Cy&v>8ZzI~Y5s(G;3!{d;4n~*}Egxmz} z`zaD%WfCJ4_Z__|ytb2dMh{EfgFEXDjtXvB@+U}Po<*CphLcv}8nyXR4CRbFe70}p zl{J45`{i28xmvD*Oc&Sh%kBBj*th3^Bq*x%nxXX_dG&EIqK)3#fs?)78&qol`;+00l|V AYXATM diff --git a/companion/src/images/library/10069.png b/companion/src/images/library/10069.png deleted file mode 100644 index 3eb68b5b283825f10f3b7b64e41e776f379c1c0f..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 746 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxP?KOkzv*x2?hqn zpPnv`Ar_}wFB#_DHV|P;;F7Z``7nWbhr7lF#coD9#p5q-T-3ewYpb_a$%_el?cCTG zFIZN^xr&*EPq@OP;lL!Og-J0J|NPdtx#|f+FPrC&1@8O42Q%${{b*ffm+gzQ!4FO` z->_+V#c-*M?|^JW`6~Wrf@i)2JFNdXZ*qgU64xT84Al>u=iI{&d-+Osw5VGAdsVhz zAM-WmH9J`y{#i}uUQi(Lm_hDmbj$}KQ5Mq#zs#fZVgjr56gSV!Px#2Hl)2!HyC#>O z@G`d0dq*{eRx4~XRZ-oxTxGT9cDiGNaMU1T0^KA%-FVTJmEsh3yrWpJKJuDg}q%x2NZ694n*QC(9( zy`7nP0-Y0iBTh=%s*9-IY^{0AY1O~xq}{t9`LhS_c08`A=lQweow@w>=bP4s%N}}n zP`LfTS(&Zs=FenQwiPG37usz+pq-c3GylpV_P(dL)+u&5sXgZrK6l6c{)$%RlcE7Z zBFZ!S*=*j+nDeY^Ej^Za?ZE6-q2ESFE->00P-lGOa4a!e;ggzt0J~lw-~T_qU;cPOoHsTY~&FAZIP!RCISzdoh1*Qy<64!_l$I_CF{2~U&l%mYUJO#(xq|~DHy8Q4c zpu8wZ-Z?)vH#M&WRY8BI#{r-MRgi*|#FA92KidPDH0 z8wnqbzi_^qaPa0Qj-5Z+dICQPthD@c_U_6_@Ahnws_WoyfA`&=<^PqLd2tT)j$wul z65^tf4?5%Cq+1#t5a8r~leNv^+`ERW3;c9=j&Cl0GG8t*xGlTMM&z?}OpeMF7B2qj z<}>nH)C%S|%J}K8HwgEv*0rC}^WHFc4|AFAwH*QPqbIQY+w07!VK~LMFT~#T+rC@c zR}LKBFe_T&osqa)-B}a2BRR{=1a2rsXVj=y*L-TX`Eb;5$)=;e+rO;UjsF#}Co#4; z=GLZ))6Oe?p5x>>RV#QfYs#^JA7X3?WsEM7Q`kkEc@8f4$D1TR?LVh0|8`%wvVF2U zjDI#~K0N5YO|N>wI_K9)OrJmQXkOcX@ugamk?m#OkayFZQf*p(rL=l-vz5K|el;vt~5Ac6KImfl(_w;ptmO1ab)%tv0vhV3H z$^6;(TNr9iUn{qLF|{W#`o{m4Ws(gGSx#s2PrW^D>5GF?PpdNBICSE^;*zon2R8&R zKdI0r_>tp{yz-p=OjRbnzo)QGlK{r8NQrAiiDPL=Mt%{4V@gqGVxEFyZc=JddR=~a z6i{9iB=4M`o12RdP`(kYX@0Ff`INFw`|P4KXycGBmL= qG1E3Mv@$TbGFSE+iiX_$l+3hB+!~f1Sn37Tz~JfX=d#Wzp$PzAG9nBB diff --git a/companion/src/images/library/10072.png b/companion/src/images/library/10072.png deleted file mode 100644 index 82189cd46fe5ad407574669a84bdd62bc88c877a..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 705 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxPeS=2F54mYxgrS zFkbLjS}v4Teh0nK3GfeFEi-O6lj5o-maiKg4)*<&@Ja9=R$- zH*in2YPyzmFo-9jgD1RZX5=jU)ml0nFE4i)|4#GV5H7s*E&B!O6|353ggD0~JejS= z)|%U@<;EhhsNu(Sox_^n$_`Xr@_ET3!rpeC-9+SJYu18$3#;yEXRtmA$@n#M!uC7t zGo0m$?>v0Q8S(06^v%b{VcHL-e~YcS@}7N%;EvxMQ^e-II8yL+s`rb|1Nm2&o_IfJ zJj}&VcDi$Qzax>q|<=^RYqOwBvhL7dORm=jelU}ZT%{(jGJb6QN(28k%N1p7pxDa>H zQsqDAPlnsu_~+&GZ&Eww!#;Cw_3R=BRnFWZ_A|@nZAHY=zE`uK`k?rB!6dDneSZv1 z%CpZ{8$56>mrgchNH6vN;4TpV(z`;|#O8HWedapr36pz2-D|PE@$jD^Ki`9`@3!Ap zn-ccC;Eiy$vNu0-P7a6ihKadl%uBMLI!*lidyB7ILPl4Lp@ZsjRZg}EZ+~$qYb0Fx zEa4>gB;!WLp_fNmC4cgLkQVOv&phR3__tne=K^3Xi5D?<}26EkfCLn{M=D|2PPp=ij>PsvQH#I0fJfu&wR4Gf;HelF{r5}E*Nn;Ito diff --git a/companion/src/images/library/10073.png b/companion/src/images/library/10073.png deleted file mode 100644 index 37f11ea34e3931858ae10365cd06048eef025e41..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 734 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxPeS=2F54mYxgrS zFuwJ4aSX9IU3+O`*KG#@h6{lubJp#cGwGbb!@sP{ixd4)PdyR7bC-Qdq2eOmrXO5_ z{~iBmXO}EE_CTH^v9){3#6soCu9Gijg=?D!ZZzn>IrnBHBcHr~W@IySg4C>=$zO`D zJW!s--lS1gxo8LLsdN7hJe{Im&8(Tm-jqJIULk;CW2?M8r__RAZmY+&^L(6{RzBQq zH)W%olTC4KSo4d9Z?S$l_e%~~2gn^PvuB#0FnKzg#6O+|mA_@CI=kg1NX_Pv6M8fG zam!0B9>q87?{C=Ao_~hn>niKNsSbiyWVf(=xagFVuzEM2tjxB%HcaeG+2liS9sVUz zuFS%|i9JnmvT#lui5NKZ0y?)t65``15dtcU>1=O`BeOJL00qDn(3Acq@*RQ_-3i}q%!bb znX^<$hIzyOCQf$UBk3C_{HXrnuV~x#(@2-?LFvKp%_hl`W7{<(sfe z;PO?`ia%wRZ68D%Bpm-b9B4MYb0PRI|Ew49q(Vdl?^tC#zrNwv&z1+r4o$o_HED-* z+Zo%H!aQ@d`MjH|xp#Y&NGoho@UzvinO!(hYRcX@5m#g1@G6K))tGMKTg}HL`iI$` zb>aTZ0Ebt=Bp_1a8d2g{T9T1p#Ne1xl$n^P;Fz0~T9jUwA07pi7X`^X=jZ08=9Qo- z=+E>x092p~Qjn5Zl4_M)lnSI6j0_BobPWu34NXG~&8!SftW3e5 zkykY_skp-0HLZ!gKWw3*k<{$2{=S0 zbjV&fp2I%(NNRI0duJqP^^r|Sm>02n$Xnp$e|P0A#-ndlxE>0ZCM=#VAY8&+@aJg4_71+pqvcKhKXi6|+2W+SL3oF# z?)T*dEc~jDRW12)$u?pIStN$g~Az7Ye7dbJe_2v^{t!eJ+c}^mTGN2W~m{ zgk8$z{N($}i-T{4oX?YI9CI49u63O0+0ZSzA#B$yxt6AhTh1KFZraPto4@2K+Yjbl z`%K=yShdOb`iItEZgZ0@uWi3^$~wa0L-V`%+bp+Mu%EuTMSc-OY}4vpQ4g=n8600^ z6xzuwa)Rq~q3nWJ5qbC07+>_vSLvGhBbXxe{&vVUX#7-N`)YUCU>p<{sxcO^XC*RSr?pNuunPQjm)|g zq5qr9YKl3_Y}9t}UGUXYJbtp{!K!xNuT!5D7>h)@9@DpQ4Az_>c<0-ORa>|l3i*G% z7hD#&KPlhl#=oMfxZRZ|4Ku4c-cGPOBWrN_ALHcv3qnhtKV?pzhK{L^F$sLO|?;K_3SbPgOcJ-vRLSaG9Y!89e!4n^-<;8s9 zkaM_X=F(r={LU-$@s+h*Ig+2ZUtL#sS>0f|XPxoqv(snVAAbLVWmj|QGMo3!4>`S= zO^+^WYKrOTYgsVk`r^Zj3MZnoxbhkjsEW>FD zrr9Uj)~2@^P1^0t)N^~$uIsJeq-)g6UH>-NOgM5o?QdVx=bb^jl`d%5t}{LToh9m6 z)GC`>&Hc6SmRu9I{So!VujatJ#&X4dd5>BC#D1(w77i#b=wIqtmnRT+rB0zhZ_kXk zLKy}3Z++(6Qgq2GWD$EE-_Gg+A$E4l2T{!lHx)U(wk`BaP-igpciOINv8RyfV|Jgg z)alcyjNOMawK_OkodTS^KMA`#GVgCuvWN{zI&w+AGUp6)OlkA zpUvqn${OFBo9zzRH_K;6hc~4?Kl2?Jbs{CM5haeLB^mie42~&9nTdG{j=4#xMd@|< z;ZZ<&QINcIer|4RUJ0s#{!EVpKn1EG1u2OosaDBFsX&Us$iUD@*T7KM&@{x*%*xQj r%EV0Dz|hLT;L2RtZzvja^HVa@DsgLAdSIy+Py>UftDnm{r-UW|8Il7u diff --git a/companion/src/images/library/10076.png b/companion/src/images/library/10076.png deleted file mode 100644 index 30bd5f62f318a98fd66d40687b57fbe949b79c95..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 704 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxPeS=2F54mYxgrS zFrN2xaSX9IoqEYWTf|X>;e)u6N6ghf=SPoYFpbrm0n3 zW~bSN6SY%v6ef6`yY$XXZc}JNzer!oo#%VZXYamQ+THr|)X1dBW9ySN5w?QeqVh*Vx&V0vtL=PM`gE)L#)l1$8+P;9%$T=op>$=%0zJd0 zBK&3Evht1`PV(hW2aI*)pDRY}l{Y-{y&&Z{&ur5f`zsDKAGB4NXa3Odtki}bvwb$Z zEB=uak2G&l+JANu!?Vvt`x#vu@L)E^mn;Fp@<|Tq8;xOG`5Hix?bJiZT=P6dZGt zQj5~-^24Km@}eMl=ltB<)VvZ@1^t;G2Y?DxK?+h5OH!?pi&B9UgOP!uk*KN`d{N=it z%fM;1Kz7EbT=7HJKa3BsHz@A>&%hnP{>^&<*NuZEY?lmU>>ReRGepSs%Q?-<-KYKG zW`;th!s@y!3^iP8R~}^Ax-y@r-ZD)~;NHW;=>AmqPr7*xFC^F&u$k|xVaeJ1PkVxh zj?VUXm$db@kFasF{P`+ssI7dHEoX^r2uJanl~)|+otElb{EyX!ag&Q~Qt|pD-+?|C zDRGS`aV#y#$S-1WOexAt%u{g8O-e0FugedQ0?Lbm^MPz5PS zNi0dVN-jzTQVd20hDN#uhPsBPA%S>$Ho45`qK8r)!4XYY4n8aYKIP_@oaK8@GrKwaD}nw zLnn7f-VA1=LpiM5JH5Sl4K`l)eI4y%9ig^j9iw<;siAmCE`zac>^6l9FM|Yb@^t-O zkaJkPj#Fd%1Lmy__t>=lbzxyj&booZSsQ`ntecZ+wz$g^DauUDQ*g{p zN-avS%MXtN%8P>Jo%3^ZQ}aqt74&C%8~`d%1t~~LEJ?LWE=mPb3`PcqM!E)ux`w79 xhGtfVCRQe9+6IPJ1_oE=%6>!9kei>9nO2Eg!_oswy?`1RJYD@<);T3K0RSP!0J8u9 diff --git a/companion/src/images/library/10079.png b/companion/src/images/library/10079.png deleted file mode 100644 index 387dc81beb155a658bd33ed44091cd043c239bbe..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 594 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxPeS=2F54mYxgrS zFeZAsIEGl9ZoOjb$D%00{=wbAJGpGn!8d}>*osBWKQc{@h%h>qY|Va^ag5 zjp>hrHrV`}k;-N=v8CnDA!Ubu3?ZgJShrd7?^k0mJ9zN>c8*o&8EP5kia9B<`!52}%-t}9(Pl@OGs{YS%i#0YS%sXZnrAaI*$C-5 zaNp8R;Q8>XalT_d>)r|vYhDA6UuPIN`HVX_ESx7lxb@_*dWKPlAltixj?xdCRx`Bi ze#sTiIpJo6($`brr9CFbk_C?)4bM1Oozr083b>u;T(?lNjU!xDqk(0H!#u_|(G|Ye zbsZYo7EZ2We6diUu{x@W({NT}bGBDTa*NR&-<5|si}ZY%W*Wa%64AUDX7DOt(?5%6 z1?(2G=?ggS|DMhC=GR|M=N*?PM>niI=yv12Siqk3{~5C{m}<;l!1YTih4*T3_!_3u z|9|jg{a|ERRKl}hje-C$*hNZQBT5`gOEU6{7#vfIG86L@9CMRWi_+`z!=r%mq9A$a z{M_8syb@Fe{h1yIfC^MW3Q`hFQmvAUQh^kMk%6I+u7RPhp=pSrnU$f5m5G_QfuWUw j!IinP-%vE<=BH$)RpQpL^uSUtpaup{S3j3^P6T)VCV?1@$maS6I=;%^d&So)DFkpu{8w2x$&q-a&0{N#lUsfz&;J@Tt z%dkT2z;f4#49tw7f!!=i8jCnK9TAz*8^|wGV%BoURpU^u$6OwP;*~a63^(68sBrYN zpvj?Wb82di7exQ~`HoSxCU-sig}Hn7-zb{9_3f>DFZ;h0oWJ$W@#}_N(fT(cpC?o& zKX_Rqudt=s>b$tm(t?9>>C8KpoW8l-XF-g9diBI_H}un`^MphaO3U}&vMHXt;P8U) zIa?X|N?GPwO4PoZ)3adl|35s(K5(}!^6d;woiz~{Ya%7C5haeLB^mie42~&9nTdG{ zj=4#xMd@|<;ZZ<&QINcIer|4RUJ0s#{!EVpKn1EG1u2OosaDBFsX&Us$iUD@*T7KM z&@{x*%*xQj%EV0Dz|hLT;L2RtZzvja^HVa@DsgLAdSIy+Py>UftDnm{r-UW|Qx*E} diff --git a/companion/src/images/library/10081.png b/companion/src/images/library/10081.png deleted file mode 100644 index 66019bb708b28cfb4603f73abcf49f5a6a334f42..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 521 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxP?KOkzv*x2?hp6 z2~QWt5R21yCmH4)Q4nz5@A~jk?zYbULp!$}3gVicxq0gPrY)}P8n=oUSVcSeq_M5v zvY~Tzh@%s8|3l+h{41n>a0>+Vi0xxxbLMqhB)XyI_F~0d59em=WUfnGckp_@0#l!3 z!%fD{SsCTK*;?beW#%+&T=S>xyi|;L!PA|o=cS%rG~iI$B&DykhfVjA?0rr5^A1v?iQ(^F z9}=E&MPYjLEZut_P2V`~IxDxDTWEpbrWrewbEiLFxNnI}L3w1;&H8{AG3l%Oq)hx?$7kMpadT7G`-1$SuFMHPe#%VUar`NR!0Rv8?#5JPC zv9u&3zlgyxr6@BoPr)%aDYYoQEKdAc7@Aobnpl~bX&V??85mrdEBg&aLvDUbW?Cg~4NDI!^#W>O N@O1TaS?83{1ONl8#q$6F diff --git a/companion/src/images/library/10082.png b/companion/src/images/library/10082.png deleted file mode 100644 index 5ba72eb8f9892b971789f7b68bcf08c985cfc1a0..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 949 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq*&4&eH|GXHuiJ>Nn{1`8H%0JQ*x8eT9klo~KFyh>nTu$sZZAYL$MSD+10g0sLQ zvY3H^TNs2H8D`CqU|?XX_H=O!u{b?-^2Yqj4kE|)Pgb7erNMUa!osd*s|{kEiq4_p zh9z%K%~;DVBr5DYwK&v8{7O$l%anhd9)B21MOI3ly}`ILula-9x{8fgAIqIjUoK## zGk4AJpVjxP_m%U1Ip6%B@p<=y2~PQpB3pDi(>6=REWK(yx49|&m|ADT1T_~oft3v! zOwFD)CVbjTah-<`%uPKaueq+VELi#ZP9-+A6B!ol3%O?}9ol9$`^g9I1=Vw$cb80e z3}Cw4tWvySyT?MUzZXv^Z;q^Zvr@<6u;RsAryCCa-pTsXZgxq(YU}EyPQlN%{8*jf zKV4KL?@m(Arlpm*>sb4GK^8zPMQy%2gt<=Id#;eucGt2ir>@&Fg;iU|tU%`<{mVC=&YHSGAt`u?-gZYzF_qLa=NSJsM6G3*pK)0-uu8`6NT==N(k<^} zFYNZ#xyj93$#UPf?Q-Z1opj!r=FOd-e$JonEwHoX>ZIVO`|}rMJI>Y%PYL|7tI=94 z=Yl4eZtdGE4KKDn_-%E@HO1NK=j)8_3<2izYcs1~zM7z4CF4G~S4cwg;k5Igg;w*; zyLo9Vhw5B$!|8X{sIQtM`gXorhR&I{5ur=(+bF*fin-tLcSCH`&6@lp7EwHs9Bi#N z%Qwuc>9zgCwqn*g;#gXekzd5%m{OFPn5W>Fo0M9VUY8#p1(X*B z$vfxg=BDPApepFk^f&-ipbAoul30>zm0Xkxq!^4042^UR40R1nLk!KV3{9*|%(M** mtqcsV%$5Cyq9HdwB{QuOw}zz$mU;m-FnGH9xvX1AP6Je{{NS=m!4~#ItwVP54+ad5<>uW5PPGD zpt`11oq}^GrF0#GRD6wW0}`okI!%29%-KTY7H$BXGPaU|8&k(Z0AoZL0c9uv$Sf7O z#Dp4jPg*Egm8;b-`a zlZ(+G0DvU>;BgFuQ=r+Q_&gT~CDaKv2Aobf@9iKN6mV+iz6XJ6JrE)RdNhCt?K7jA zU+0fR0A+vvyAx4$y29-YeB|#E;j?Q2FOj5a`pd6|NXY}A^ZK1GV5?(m6!04gj_V{1 zu>5F(@QViN1VG<13AVH1Xl8T`&zxOFQqw$e_(6ARj^V}VhLQe5$ScZz$2jq$7-%rl zgArV`9%$HLGx@e_pZbl{wS^1*&uFAftN_5NC#V`X0H?jx8~I^nZH98CyZ`_I07*qo IM6N<$f+q{hRsaA1 delta 515 zcmbQpa)4!m1ScZ{5d2!}bZMf#cs--Pr;B5V#p$UR4fC1}MA#mDPtr`;kaUbk@C!$e zq|#1z&-?=?0$AO7dUgs0hAoLvTp?ay&gPOWCH>*Fz*pV#|5(1|OFsw{G>e+kozMDd znd)mvSr!a8>4DZqV9x@^%alucDOVhV(@nwoZ7e${1;HO|ulZPhU1>IbU7jbyw>~$) zTXB{`WJAK=8On`c_!mj)IEn}_nIO5tuRAMadPYLe1*wEb*=+CUCOl7TdUv7oKy!Z_ z%l6YOdmBGhWjz#+zB1v-n&mP#fuSr?;u=xnSXz>iU&P>;Qk0pPr{I{IlvCEuX`n3R0DlSdwa$T$Bo=7>o=IjdTqRbq!5J49%>$Ga!C1#*LE4K0Elk2mOf4?zRY{M|H}D!>++@&T;qK&;)fl?6X%0*felcgRmJ!)Xk_-Mz(R|_u`CyAcYB{Z zE6Dq~RJ;;h`6gN8z#_)DmNT9254SOX>s8rNEBK0SlfK2Fk~E$b!VfD%^CVud@vWWr zB)FfqWuNox=?l(2xbmm1Wqqp8VV0zGo4<24Y0v0d^lko!=f(4y+LQPhtWNXqjCwe~ zaD|3#Y};jVkrv%e+S~lMoz-k^kYV`Dw*K>>CimC`yZzIgvp)yC;k?PQOxUu&x^lZl z7Yon*XUwyff4Y&Q+rDF$e$fs$9+MCG6W>^w1sq!^^M(2N0c)8P*YCYyQQ^LEIY8;Y zYKc^<_^;sDbU%a`p<~J)pP*2e>%l-aMu;bg4IT|9o7nmHRulf`--D9|MJb}@| zX{un!tfOT;e+1vOZaaG6#@0W|RjFYgB^WlZQob?S{&7~pHHZDmN$Qz*O*Ry}9|`-F zefz+(RUJ=Dp3Z4p%CA%q_5P{$HP;DC{+Y8^p7l(-$#!Q_)27MJ%!)2a+|m-aGPvUV zBn%HcS?-m%#xme~8q+QV#t-!e?a%ycc={v$H8U`Yh?KZSlsJ}_WaJkyIHnY3Cgv$P z<|d^UrPt+$M*-zULGsS|xw)x%C8!GeGd&If6{vy~q$HN4S|t~y0x1R~14AQS14CUy y(-1>5D?<}26EkfCLn{M=D|2PPp=ij>PsvQH#I0fJfu&wR4Gf;HelF{r5}E+XPc_;A diff --git a/companion/src/images/library/10085.png b/companion/src/images/library/10085.png index 644b1d0062751eec18790c349a534d09e3dc3af3..073c3197bba48d316f2f26aef88d9e4c3ea925b8 100644 GIT binary patch delta 510 zcmV-8-HxZI=HPa2sgGWQlw_mjCj1ts_i0yX$Lfj@k*!N)EFIC1H4 z<9c98e9u781IyxH8DLipz~`MV`dqIAJrMMEunPRk1J{42U>Io1a$qI+-5bCv0uCRS z{5w6sd`AR}5Dge#cmG+W9V{1rboGy*99TjA8wN3ZU={cnR3htZ0DZ9?g9HTo(W>GP zQ4fM`*Z`0mDpH`erc;1{{&N%>#2DzVm^V+19m=L-=InSv2U-on9s=}O?P>G>yv&l( zo6i%qW3qp2GQu$-L~&bY(fp5O_jt=e+!oG8VBq@DcZXn0Enfdn)jC1I&tcbSFo{1& zfNl2FrY zq-U?}jGT6d`9@Z0zmj-7%WB=F!jn0bt0v4<{J1S*Q+&dYM6nfiJNqs$M|@Ar@S0~2Axo- zf4$y(`Wv>4d%gXa*)qSV$w(YIIh!NLb3@#9h3VVf8>F5vtvj$rLS}Q^nzRKkZ(a^$ znEP^W_ls9f?iaSz+_{8O9U_#dkA zzqbFtoF`S{cv&GZ1{k^`C9V-Aj-@3T`9%zlDMguyc?yoXNvTEYb@|~@KzUJ+ymNkT z?!;vA90pYoFD0=g)hf9t6-Y4{85kPr8W`#tnuZvfSs9vGnV4xC7+M(^T$wBT4X7QV dAvZrIGp!Q0hNTCVdI2>sc)I$ztaD0e0s!gz((?cS diff --git a/companion/src/images/library/10086.png b/companion/src/images/library/10086.png deleted file mode 100644 index 2f16b8b80ccf9b44b580263fa8940ddfe2a01373..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 713 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxRpVe@%FN{ZVU{J zH#}V&Lo80WUfP&<+dzQrLA(M}S+bkB#)5s0o3}bMnEGEV>zr%n_)N)QX$9{Eca2@* z6Miu`YDmL#HHa)$O(pDt+wbACDET@#4#J(F%*Ex46G0r~zK<#7~ zpC?cAlPN~t4jlrH6Ru7;!4Nl7aUx^Py}9lQ+`o-(UCM0NSfM!IH6Tzx@WcEM)dEjm zEi0;Gk2^bc<59ktypZjg3|3DjY%@5O)KvY8wOL$XuGyuJU*^0ENNPD#aUfl_Polwj zLDCGac}5tP|MBC4SFwNp{W`yT^UuuKdh5d_KfiC2 zi(fBxnZ3=*ruFpF`nx{2rsk%r`(B=7WBYCY2mZRF46^e=1)G5pFH+(fQQ}xyl96A; z;FwaBnV6^Gn46SZlwOw~9tD&a1<5<-=jNv7m7pr<&-6F|RG2bOvPH86O(`njxg HN@xNA#@i+h diff --git a/companion/src/images/library/10087.png b/companion/src/images/library/10087.png deleted file mode 100644 index dedee12ff0271973aae7509e4d829844dadefc64..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 611 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxRpVe@%FN{ZVU{J zMV>B>Ar`04UOJt7*no%a!Tk%4?oVGZvEC81a$s0LNzlka;N%Ae*@cTk9K{0tY^OQ! zhcY_q{5|13Yr(!7{~WwjR6qQB^0il6CED?g_JVaSJ60<(tunP)6&n-W7__rtP5agf zqLV&mD{3Fnd&9k8UR>9d1m!MQ+vUp|8aHb>{0pgSSW|D;mhpbVnVS`_-V0dgA2MQK zDYH8mk%KKbG6ZBrD_9?fH1IfZY+w^W(T&0mBro@!_+E!NL#TKli&d(X~j{Z`NA zmme6OSAO96?1oQs`R60+mMf;($T6>(@{xhFRwpkp$66~-F?VT?(xVl%g)fCxFWl7{ zpqlbRNXUm%FqZSmEv~9{K{>3Q+7JHo*Y7M>>fMxZtP~g}A|2>+xQ9yZ7ki2t#Zf?)FK#IZ0z|ct7 zz);uFG{n%%%Fx8h#7x`3(8|Ez%3RrRC>nC}Q!>*kacfw5V5t{S1B0ilpUXO@geCxx Cb?fo~ diff --git a/companion/src/images/library/10088.png b/companion/src/images/library/10088.png index b24fe1a0567f9ed97a78b52ff59cc69d3dd13a6b..7bfefdce68dd4179239cec2fff4239c6dc0706fe 100644 GIT binary patch delta 401 zcmdnSe2IC2gg6Ha0|P_F{q0|X6jPG7y9>kr_Wm>bCn`z^u$OrHy0YJ6lHgJ?T&6RB z>11_A<$6XZPZ!6Kid%1Id-F9L@VM9te&7G8q}_oritEO)nK}v@9#iMrPnHl}!fQKg zCId$U3>}z}{OOP33`z0NUoT(V6T*^E_;(xAQn2(DmI-VBHe8fe%KOcr(mQS1^_uy2 z9ZqNeTOG_`&T1s*-x+>V!HxaE_azMe`|Dd3RA+3enCy6TQ!3Z94%^5Mt`7`6a+fB% z2p)*uFfEiZY(3+fJzW773ynH{p1W&xAWLvU?u*?HPZB%WeLo#Cx^bQBU*p%U33 z(QEz~b^P(O_s3)QHi`+JsytKvhAaIq$J-lX$GKQ{{k+!oi;+oz0f<5wE}XFlFW1xh syUWlm{9?;Lv*jWJ42%#YQCh?Bm(`_vW1040V4yR2y85}Sb4q9e0D6|C6#xJL delta 387 zcmcb_yp4H+1ScZ{5d2!}bZMf#MEy}u7sn8b(_1fX>$?o6s{d<*an`?f;8z~mSp4?F*v3aWhUk+ zIOZm$7NytaherYBMM3h;`MJ5Nc_j=J(}i;wR6!ysi6yC4$wjF^iowXh&`8(7P}k5j z#L&#j(8S8bOxwWF%D~{tT-k3xBM=&L^HVa@DsgLAdSIy+Py>UftDnm{r-UW|5Q&y@ diff --git a/companion/src/images/library/10089.png b/companion/src/images/library/10089.png deleted file mode 100644 index 133c90972f2212842e0fe5767dc3d690de22a394..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 573 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxP?KOkzv*x2?hp6 zA5Ry@5R22bmv>KOR^(xOFkew&NlWg-L#MYbEoR*<8{_@@MDCj&=>w9Co2@v@CMZ}K z)o*K&lUS0j?$pAVBi_`=o!#jEO}y*$7jIVYM&k*BpBXq6nJcEU?_HnYCTz!BaNukM z*T2I*!*gVs<}?0yy`GWlRprI@?kO@t#!Vp)MedolX&-I&TlppOp!S;8au9%R;_qls>Q@BOSkpiyWJrV&AT297kf4uazE6&Y&@1+{&`?iSKKfDU%Y9_Cd;OnW!pvM&cEEkS7*T!r~Ne1kmarFrE>yX zZ+o~e*z&?gtZ~n)BN8^Eu~+UL@R{pq_acsEPve$T&ZZN#Ut5*8e=nQVKYigTk`0RP zy&JY~anDq|F6k%md_t<2>+xQ9yZ7ki2t#Zf?)FK#IZ0z|ct7z);uFG{n%%%Fx8h#7x`3(8|Ez%3RrRC>nC}Q!>*kacfw5V5t{S O1B0ilpUXO@geCyY(A$mx diff --git a/companion/src/images/library/10090.png b/companion/src/images/library/10090.png index d45f27e5b7d0967160f3e4497f3e30f6589e5a8b..d44f974b54008e0bc023360d0e1d73e4e4706039 100644 GIT binary patch delta 544 zcmV+*0^j|_1m6UZ7#9ct0002@y&$6i0007FOGiWi|A&vvzmXvq5da5tNliru-U1j3 zCNFLkz(kX^0V96_&q+i`ZcB+-fzGk z3z)pWfAoLz$tZaEzCjdBZTvjB`6(ZmSowN3^K(u(vGe)jUsV^fmk*>!9RtD7tN(`QH)K8`V9o7xKA(tUVU}9p(}`#)8Y^ggR=`p;miXilgjOP4OEd=ne5(V( zLZz8+T&fkIO~{*hbR{_O?+;iSTs1f1;? il=w;_@){@$s2=}fCyRH}E;sQ20000$^Kj+39$>6yO~{O%8CP%U z@k89CxubkBpSIiX*;C>l_;w%O)UbBZ@};`m&0%bMU(Xordis{-&hzX&tj3CE9j~V@ zu)q7;b|vRM6Ny|o`{}E@uP>LIbud-seL~mj?|bHbVA1A|nX`YR&PL|d%DvCe{I6bk zH}6g7z5cmJU&t1#Cw#8**KWR7%BKG}M&iq4<9hB8`{>;c%gcUA+ut^mw{E_m*1^Ay z-Ec>Q`vuR!fWSaWmKklQ6b^8Nur)4S-`;B$AX&Vn@zjjPywA70l{y3nrAcm1KIvg_ z(`&RdP`(kYX@0Ff`INFw`|P4KXycGBmL=G1E3Mv@$TbGFSE+ f&`5-a-29Zxv`X9>mL6E@1&VG@S3j3^P6Qx$}I}~q9AhX1Jv!(_JG_agvtNSp?SIIGGiE_m$ z!DyFBOU^6^Iip}II4SX7gOHI?HG|yQsm1|wj z_$2rG9CteFy(4*be2c<|I)<3b7Y~;^wec7nPXF=Udlyd?%cTS5*SRM$99OK@p5*jG zreb=d&=<}58Wt|~KeA{1_nb5Rmg7S4&oMKm7@7x!U$|Q7##gAhO2ghi!%5~<`MvqJ zoC~%bm~U=V-nYIfGp8jhtX1+>^mAE#+4Txtcb1iHXqtR`vX8k{u-OD*z8|w9Hi+@X zFGz8m{6ccM>|w#c*B@DaeEFJqv?*3UB*lG7xYYIUd3}ny*QJxPYk4kCwa!gH-1H#H ze(%>5rae!ZdGA&){cRi~b9h0Om;ciIwK}fuqGEZ`PiLzaz1_^(weUj?&qt-hp{r}^ z(l&lCs${CWKFd5uW6!-nVZqjv@=UXK=0&v$Kc5E`^0YhT-fq(q+jx0X*2S9LS!;_e zzcANL52{$N_vFHA^KX*No}YWZVehTWKiKZrPCk76*Mi4i7OHFo`Pd;Qfg6pU4D2JP+k-y@0_2To0?aGs-Qp9;{Z^BDo8;} zVo9o1a#1RfVlXl=G}1LN)HO5>F*LI>G_f)<(>5@)GBCI@SN0oIKxm;OXk;vd$@?2>_u}OFIAn diff --git a/companion/src/images/library/10093.png b/companion/src/images/library/10093.png index cff628eb36badeb8bd272864e7c9c7a0937c3125..787d6cce4582a1241680a76bc3d21453f282221c 100644 GIT binary patch delta 323 zcmV-J0lfa|1d#-gEPo>a01G1l+or8X0003XNkl%h|;e{T-Qxy>EoDDZDBnKdf4KZ_#NXQ~bKqX~}QYj-0L0LLL9!Y3TV=hn$kDuP3 z-ZP-_U~8cc5!HaIs#?L4nLrSERdHtxrDXzyIB=*sq8gY10e@*yIR2*8mH`2T%1J=C zEsufsfdlQ0UNW%%fEOK(&oxl6g`9~q4Lc2t_QhBOv=LIc8f-;kdG}IiAPd&-LKeIa zw!+v?q9ONAS4AxpekNzRSOY&1}A6ZQkfq1vtYpuJ0cbAL6@ z>SVW=GFUe25jfKSO5OVLEt3eJ&79(7FF0`PhwE(0yOKht=ywr*-hn6Q;brmh^gfCB V)_lwV4d1DNbnK4Et?rY%0k4bfk*@#% delta 413 zcmV;O0b>4<1nLBkEPpcq01Gn#lCr&w0004bNkl`ZXr^av4 z!~q798%+EPOr|mJ7!pb~LF*u}NL}qxz5$7ggGp(PQAajPVw!_6bV4B{S}1tlwbt0f zL08}SyLaz@mj^IYV9vro#n_&~Ngl)?Fko{S!!6kDc4J7f0Dn|0&c4B|FC^j4=P*om zq>^C!fPg)LU$6u)301%+p1uxw7DN^R;EkifA?N9yk)pr@Aqm2%s_QL%u9LzM;3V*A z0+$;N3XO0m$AS=EX;GMm09nA;^IH1QI5JK+3TYNNc2NQgkbw!iTf7eS&HC!fa+^pK z`-sBv`^}<#;eX0VMv4@|>-C~-4P~_RREXf&BCsOoPC=zmn|6ZIW1tD;oFo01vIaGO zbl^7o{+>C#*D?gE*SvHW&pbqD*w$>R1emL9zo z8JXB$t-;asrs{M2hihB7-ImO%5}&o{LDd8^L#NGYWp#f0u5D9PdD1v@kNjt$b1_qF znJd{|l}L$XmT~>|M$yGGaJ+&Z~J||q~y?L@vo*#I{zaWJ_Bdq)LMlr>g zEC;r4urc8AT*6vrR#f1j5Hx9~{nH20nM{XTlb&d#Rrh6P%g?*{Gm&rpO0Kp5@4a40 zj+*bgWoI~LWj;EaC?3hDE3ALkeZd3113NTxgPH_h>^dNDNvCsx&H2L$XFlmZcx^Hz za++A<9M;t8d(557e%@jh-C(N9?{he=`)v|WO#F({2esN72?=U##WC+hKQrw;^Ke&I zWdKu-c;SoBMzs&721$o7f8!2Fo^zzawMSv!y&oPW2Y>T-{}XxHIaM%YT2J^!%Wgl; zYXx0P_M0f5@@+mEZz{F>zV73W($sZ~xwnEHVoS=;wCvS!k2PMO+9sOFnV`r&VeSQ{ z9MxSX`cBx3%=~}<_2R|Kz_cn-;u=xnSXz>iU&P>;Qk0pPr{I{Ilv_j3Q~}gSdwa$T$Bo=7>o=IjdTqRbq!5J49%sc)I$ztaD0e0sx*XcUJ%a diff --git a/companion/src/images/library/10097.png b/companion/src/images/library/10097.png deleted file mode 100644 index 88aecde84abd30685884f17be0025b7cf0eab96d..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 953 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxP?KOkzv*x2?hqH z6P_-PAr_}&FP+c6oFKveVYzqav-SJf^+l)VRNM$m74Kdu$@P!5iJjkB|K6Px1zVo` zJ-qsUUFxn=`2H|9S-9GCn#iSe9nSM9IJID=Y*^}qD_XwSRpRfPXIdEwFv;J0UVHEP z@3s&3oyAsu%Kp-DIPht@)CMPk^~ov>!Ww?Z6;|0?I=DwKWS-iCWhNUM+ynS~?EW7S zFqxvv@gt_*P1fz^RhAC%txJ83X0qNn%(Q1icv=I;)dxK~D^DvOJ<%bYsCvg)e9{ho zJ^I)8ESA#k9No4V z@^>~o{jun^s_BW3!Qod{imgzYuJhiNbN=R<4a`|yD>NmJewrS7l>Mhr-CUQO+|P8c ziq1aOY^JTWFj@Y%q{YE$+GQP!mu`M+b&4f?T>$T^*Z%uhS6wW~y{c-l^6s7OtRXBJ z0+#CE)-F_aFv(*sclmYRJid&jBBn`KYUAb5_;W#1%CCu(Pl%KKeCVU>#Qps9g$`y2 z_^n>7Wz>+C6~$7zMM2E=@Gh~Z4^PJAhKL_H0>zMNS8Eyq@KOc2w|oc8MF^<58) zKJK58RPj^q#J9Xd7XIwJ9;lmI6ihZw6K9fg3j4BW);p#=9ya|~8_N179QRRw{_ye5 zR#U^?O%jLS>3Vo_-KRe#4!2}XXTCFF{WdQvyFor| zdeVv|$E})gU3u+WIMvGKB>T4e^%X0&UAxuReQawNL$7KShpy=oP(Z zb8gxh?vEGiH=T^$-FGeV_=k4Uz9s3m9-ejOd@2<`le5;4ZT;mfU24laB@Dv0uRH(o zVXxd2t+b05`n7E%G^Tc^?JL;M-dE>(=&2mbahx092p~Qjn5Zl4_M)lnSI6j0_BobPWu3 z4NXG~&8!SftW3%(LPgL{KzkN{kdp@YDD0mp^NAgBP+z2pd3n!lFr00<$KE^zia?}B#$Gzgqc zu5RRA02cy8e8731p2@oaTwu^$#RK1>ksR_|R?4WFV0mJQakO zL&w4ii+X>mTm!g8{6YaJK9zcu?dZU4Q`6d33$Q~0qe_xFWXsb+Q3WGaDcaAu%4$F3%i7B1QJyhIi@2=rg)tOcM^@JC7bIjg~xEuN>!w|Hrc}Y zjKzOmb}^i)>I%nU1Dhd`MME~l1<<<0$Zr&eQ=f4V9J@eu@F&Oh-h;pgDc^TN-j>Tf_-AUY z0Qe}r_Ypif@N&GhiSV=s;ud{TK77>!ORZ{vdtu^&`?QB$fcm?0%fl4-bA2Z#PgAh6 z(7xh)+ylQyzG(7F`zHW@r%p|q@D%{RBlTp)w$Sy37?>+K%08Npr{SCqXx;$PzUYBr gux9Z)Gn$$G03XsaU~lDI`~Uy|07*qoM6N<$f(H|F5&!@I delta 745 zcmcc5wt{Vf1ScZ{5d2!}bZMf#cs-N3r;B5V#p&2fd;5e91=v5_{LC5b^5(0fk$jEf16LLdWW4l{;w=O z=RA+$x)(~8=hi7DaZOH~TdMcqThob4&tAWuWh-Y`U+tCh;`;K&$r?3wF`AdQ{OqYW zpCP$Od$kT_uH~gKZ@z7jscSTG4swWGA zESz3*f76PWPn11rX4T(S(BQjFD6k|Zwb6G%PW@xUl#_K1$GBZ8JF|{;h3#d}ka1*S zuMJ&PmQuM!@_vl1^iJkA60*)yMgB8L=uMg|CNz~Pye-tMLFIg%*P=BQTpxsL-M^eu zIr_c9&B<=xf}BauWEV`5y<+mrDC>yzGQqNlaB~|@DeZ*(=#m5HuGc&cwB0mAROfNn zy)}DG*0|MYEmGg(`cA>XS#9Q8h6=q6Ju5UfxgA(Kk%_hW3hVM^*1TD-3gi0saXGBW zEr^@hZq2A#JJHK;=Jcr@i%q6YbiQF!VmKvLN65~5%0s5&Q#bUsGX?EjrZDe8+D8tf z201~GgVGFAj&pd@)-|&Ucy`5ct+7tXe6c3`mApv!+r;{M2{U^`1otyqUPBMEY_hkCr4RadQcVzzFaOiBV{J!M8v-XP{ z=UchFGPePyCy^4@h!V%rl8pQ!2FH}5%)~qe$K0gUqV&4_@TiI5$~g?GAQdTzC8<`) zMX5lF!N|bSNY}tn*U&V?(9Fuv#LC1>+rZGuz~IVU*>6B25gKyyQ!>*kacfw5V5t`< OQG2@jxvXYPH~+Co?j38H z;1b@yCObKdNZKa{QXzP3;Miuwa-&t$oSp_gJgZwOtOD)2t?-d8j4Q;$={ zjF}&~Io;8->t<)&ea>NVd~B-`;|8P5o8kXL^cuGpTzWY_pl?@0pm>8X=MVKiOiYU# zoi@ha?gNIqNQrAiiDPL=Mt%{4V@gqGVxEFyZc=JddR=~a6i{9iB=4M`o12RdP`(kYX@0Ff`INFw`|P4KXycGBmL=G1E3Mv@$TbGFSE+iiX_$ al+3hB+!~f1Sn37Tz~JfX=d#Wzp$PzMYULCF diff --git a/companion/src/images/library/10100.png b/companion/src/images/library/10100.png deleted file mode 100644 index 14001a79a50f76f8fec4fbc0bf3f828ecf72da1e..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 806 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`2qYMOt#!Htq&N#aB8wRqxP?KOkzv*x2?hox zQ%@Ji5R22XmpA5JaS&j8U@7_3>P}o^M5nld5Njt(WAS3w zMI52$9(Dz|>}+adO7v#zW7~7^Mb7=V@6P||xXzcSQ@g1=?cYYue@2@o2wgeEx+Q4A zq!gJYDFJgGoGmY@EK*n|yOh<7-CeU)#AVB}EloFDm(B>&P>|9%dwkvEMagekU+ix5 zViZ?cZupJGsci=LSHr*Te_Cpe2_$(uu5fKQzhKwmg_C)%vnuU!v~BBTJM7z7!P%#= zCec|TmZ_YH&Eg;{dwI~C#oW%)s1hnKSmRqTAre9NLxCZOz@@|2yHjAB18 zvnfT-Wxm!YZBeyn$AdR_%a~s+(5Srm>aMCqjsCNkw326uaS11!pUe3qs_(hAit#0v zb?e#K;uQ@>maAIx|C%mY7ZAmtZ+MCAv$~v}^3TT;yzTFZs~9i;^l(L^i*H(hy?W<+ z=QLy0^IdO*bow^MXNj!qw^fOrX?5e5gWctmA*Twr-Jh~G@CTdG$v;v(bL5;x092p~Qjn5Zl4_M)lnSI6j0_BobPWu3 z4NXG~&8!SftW3Px#0%A)?L;(MXkIcUS000SaNLh0L01FcU01FcV0GgZ_00007bV*G`2iyS<7a=#{ zU`h)B000?jR9JLFZ*6U5Zgcc8E1kAg@jxR>u+$GR4K_NKkgYG{#3LoJ>7cU{eFeOJxNWi+u z8x~|d#_qOiMM#J-ERw@|aac-*0B}ABL_`3Sqa1TJL_#Rq<-eP;!ej%*Vkd$n0PAs6 z0QBKFV!>-AOrvKBNkfkD{NQx%Z;}vtgydSB7HSd#kO{!Td`$Q~fMaw4<3hC7W&c}G zbT!Gqe*}<0a1TKMz`QRu5k#bzvk680)IF|{A(S$3W;!LtZJ1Oyh2^P3EmScI~saI8HiGSH_XV&hH$P&O3%@!yre zGU$45#^w8u08oL!G#%-C{ZCF`%yHpk;qQyse6&J71<(dy{o7mGYnK9KvdC2=W!oe?A3am4a@!&WOZZ&he|amT6`c zKo#Nu3F|cv&r(#W5gP~0;zu6gcmd#McySz6WG#PGG+}ddI|FQFwpQ5kEdZ73qy#uW zYODajJbX+y(N%z>uNKep$o7M^;vi-;-)_x_e!fH~ z@HPYKsG|9<8!Ewx&8glaGDgGK8OSq%I~s7N1TE_j+v{A13($T+TwZ^@^j(v&pcKsj O0000Px#0%A)?L;(MXkIcUS000SaNLh0L01FcU01FcV0GgZ_00007bV*G`2iyS<7a=l{ z3ciE@000?jR9JLFZ*6U5Zgc5B3<) zet8!c(h#RG5FX;8I#}{nLfL{F4F3RX zzkjNHPz*E$3lapnN2hM(A!Cd?2&J%|b)b^U>`X^ijrp9JuS+r6X{W-B2OVn`gpq{u zx!=5lo7ZKZBj{Oc#jur|;LSkJI`y>dnI}(sntcAyH;W+|QVyWhQfA$U9D5(q;{JSx z@I9GxVEtXpk z48*viK*<@CCv2fPGGX+tb{rIDfd~i)O1ZWdfm;`0CKFVNx8q!3U?`8qI}awXk|;S_`WJj*>CfKd8rk6ttfw-pyR?TBvtPm!R4z@65)Qeuvx|3)gP zAaDUNfx!1H&^-^`AXSYxE)wo}q%ab+BLC3Ah0<)x9}P|TxKUh0fJ2$3NM|JPEvh;n zp8ynJYGek060Tr-9AxksZZiI40G>KJ1$qwynk=}t`5(I>l5G>B#twog4}~o+0Lfg6 zXgI1*8OIcV<~s=5s$5v*)DcMCV4qKelJ%!!x!p@$e7_LG|1;n>eo$8&tPPr9k7k6= zm!(&V9}$qgB;`QF|Am0>I9#LQX9QH6TCM?mLNKxpYiFHfa{z>kFV_D7-(h!}ll7;R P00000NkvXXu0mjfG~Jwa diff --git a/companion/src/images/library/10103.png b/companion/src/images/library/10103.png deleted file mode 100644 index 8fd5c289773e56db67ba2f9cbb392ec821b33b77..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 737 zcmV<70v`Q|P)Px#0%A)?L;(MXkIcUS000SaNLh0L01FcU01FcV0GgZ_00007bV*G`2iyS<7a;{H zw;PK9000?jR9JLFZ*6U5Zgcc1n46`!)|1YZ#1Rop=+oYin+39pPI7@s;mI)|(KZl5j0NWe@Me@_RGXop50E&C? zhAgD$PU`~HHv})OZqOB8D#4~gq$aEoNQ}xNy%u#R1KgH{WNaK^0ac0^5MkeWiG~

O z@)>D7#`u@V9e``Rk4*+gY(1#jI`j`vJ46sHxVaHUX(V`#juhtWEL~=~xfAwx#JJyI z@}U9YsQTp4JKk6VHhWX(A|!;OE7^LDG25qNJD6-bnjDkxm39illZr;mLQ+p#_@*+& z05Qfsjdtdz63_^$RH*J=1L6D^9%`sX>un6mcdF(AUT{7~JuK6+A5+YpS zDE`L_iht}t;hz!C>0jX}0#U_@q?+PgPC?VGLPo@zaG{s6TUuv|RQ&>k)wBW{_CD)C zwqZunhUz^z#8iv4gJQkH+mYWP zze4{9?b=O);b$~$YByNZf~;h$&x5)(%9{muas!JA#R7I_*5wkk%GSto7!>n)4Lldg zLFZp~0KbwAP7l6IC8+hz$LLqPifCHcJ%7AvIHO@jy@p?bqT%kvV|$u|NU0ZSUOIrM zs6RKZ)^=qq@4|&5q;U<+G<**Rzy;6zSk7D1q2lHk(iJJ`W_k%58ntfz}(NX4zUGjI1DGT?DB zUj6UC{&~AKVNOT=j(KW?_{?Xxc*{~Qeo|9TeC^*YX$))$*igXk4`JUwa&jH$oxWd_ zwcz&C?QLI;57xW?Xgj+8w#_%Iqqkk^x|xc?D_$O|tT$yaW!q!%Y!8z|Y{QWs z+juLmVIJS#_=qbEP7TT&B7dhbEU@_TWaIMmQ+3L3|L=Qe0t~IV(GiJOgmW*c+ALKkqrk-;PZvkdHu*ZG@X2s9P{ z3PKXBGkHkL4s#w!heg zdjZ4dl)hth_QTF2I093agiAEQcroPja0-B|zqjHN!iaw-4O($mRjLF%$lG%?x2Y{A zGf906z_T31UnD#pwLm;4r59l6$v!S&U_?}=-)Q}P5rPe)wNE|!O+XKJY&!IPxnh7g zgWjggND2xWpfNLBLyeR~{V~~e3LvNpT;+jWL=1==p{k>Njab9k9|OM?lCw!Nn}(JY z30UTZ-$s8gmK6{n!rWCyDMd(fvj})ldJpk5nDJC)Q=5Y015WsaNg@%vDvAx(ebpM&b|73 zUXC4$Ds};3WHX{X=Q$3cJQ<4T6xTFj4{smK^A;0ag59Js|P%6ZL@P%>U7l5*DMk1)&ZM3SeW9e}J0Lwjd;ykIoMh z0l*Fao8QGIL~J~I%N@Rj1K3qejNq^!Y1(932fAyWfD(~?I}yE10|(9^&R5^grVoTM^DLQS%vkW;|f2a&s!|AMGB=ie*5YVi+m>VVD{MAH>Hy?{c5ihy0rm*$Mu@{JvXO1zMlXk-%Ws)?|we8Ofm5_ zV4dQ{ldq{T$+X{hd#-FSc-|X60v-W>FW?23-CvpQu~g^)3jhEBNkvXXu0mjf9P_>M delta 687 zcmV;g0#NV7z1z0x?pXbzZy8H@{9AE*xcqru#(!m!t{&u;4 z2}IS^fQ3(og9GrF0mxD4`pC{cbNJa#>N$k~D!2V_G=N*6xv3B#k&72w{uhR8;}Z;g z5n-(aP7`1X_tC)hXQE~})8fs~T6wZ*GciQdA14w(*fF3e z+H9jRa}MYD&B4~s0y??FRsYfOp*>Uvh25p2=D+%_Q~o~(H>-XLcXBtj4Dd|@NRk;o zjW#f|0F@P8XWE41IDo7Zv|K@lH`sMFyDh~l*mMa-^Ca4R1`N~$&{~6OA!6x&r5gn; z+C8<>@JE4vO7`kGd<=x5bzcemPsiBAj|x>y>2g`b)o&#E8h^?oBe|1 zG>50JApU+ou!;Yg0bxDqy9A5_oZiHb=u5vz|9cEfR1002ovPDHLkV1kt8I3oZ6 diff --git a/companion/src/images/library/20002.png b/companion/src/images/library/20002.png index 3f3d2186631fdcf065921163f7b188eed07054e7..ededfb8acacda3d639dcba302ec7db42e170be63 100644 GIT binary patch delta 546 zcmV+-0^R+w2jK*eB#|*Gf8GKZ3MwkH%6rEE00HtzL_t(&-tAb+j>9krWGepumuC;# zv^K_$Z9=MDwYR8A<^dQ8DEIy#A|)nxC-Up}M%6pf38AHOivuV{n;7U_;yWpjPM{KR zuJQ@g;yw6O0tU~8PfS7wo`RM_4uOvMo(XynJiC%L8NG(52n+*Fe}^}g6Nw?PF@}@% zLKGH&ng~yxJwRUOfc4(3`7#Jca5M{k(2!Yrr3u~-=79F@7y)o3-a^w0j)vgbwpU}c z!;V#f1dd`@cyt7hJ2bCJJe&jj=^D#{2A<35y6phGc7qWEKVA0-faQZIt>Ca2+kbU4 z`sno=PZ0+3S$E)=e{JZ#+nafY>7iTjb-Tkr2hNgn$$=t?ajZF`EWku*=)QVZ4X#y! zsmj!?y7NN4gT6qZhNm5@>g#FrX#y60m^~}-zXXV9UBMS+{H8Zs%3LFI2oNtlAn|Ud zkh9ZmeK^@FLv*JNws&C-eKH4JRbJYy!w2Vq>L9}2lo6STf28UMb}-|dACc`CuZ`D% z!elZAr($u%3s39xn(qVMk$mAS(hKFIUc+-8fL*fSM=ckt5$KJI`pU<3Fc k9QYFW68IAM7}ErP0BpL;jX^)6ssI2007*qoM6N<$g7%;Q#{d8T delta 882 zcmV-&1C9LQ1hEH@Bnkm@Qb$4nuFf3kks&O9+yM_4A`J{dzPW+aMN3aQ(ReF?&ffs8Du zMNmc`r^EK+jHYiM$She@L)E6KYNI^RW;3bFYt#13bSj>Z(Ow%vKiQr9Sqj-40y1~? zG?uSJYa9PDXn4By!((w5--g#(rE*%pENHaa4Mz;@aNU})K~=d>nnJ^5>m7$Z z|McrrCs(xtueYkLY$IGa43D@4Uq=TAdT=~8y0A9_FYXkx)Bt^UsklZUtJ27*4$^ZZa zfqW$f=I!+@GEB6&*JhqeXW>kN1W8vGNPrUYOOj5p5*emf-}AlYA<^lNz_Y*#;Q$2z z#}S|)gt-D)N!5`|E@VOgNCfbWN4yx3@D7JrvbP(UB>K#s2`J%!AQ3@-)6MP* z7;7q)+))?-@K6?Wl>vexM>UAWYZJ2qc=zfk5-%j3n4;1FX>z@I^T=Ktimq(T>$$F0 zkn$~2&}b7@osIUh4hG?hqIWqIp_B(tE0oCA#~qK$^;$C$AaMW)0U!>A7ziMQG@XjZ zy2{%Ns-O`Eanva;D|v5S5Xc?qdg#NHkOs5S2h$eK{e+R{1MHU?C_#lOg zQFY)HbCG3M@usMar6F8f%XiPdjTot-<%TuLb{dPOXa-6@Ce{O0yLHrWfF2NL)CWJk_>PJz_tfEaNA~r zLAwEzRgi{`v<>y9e=`E(HYGR#MiAgxhI-xa96%KEd8SHR z%VB_-FIAj6**}xlLcQmKV-#$T3@7P-G50om(vEx&+>3$@0ohVEFQ>9uFm(~~VuEJ! zX)RUIaYc~{JyI{7iJ62{brGEq3;szj7YCi>O1fllh8kX|z+IIQIubU7Ma(itcRTV- zM>KST!fkwo^)I(%SDW1M;K_A|`|yx;-PKEgUeLe=y*BzR)~fm-0d(`gCFc=;+KQwa zX1H6Ez1x`6=XO=q#xK=T9eTl*LV#8P|=0MZ&z4HPzoa4 zjUg3#stUD5lil?I+ntljelh!v#x!uj??*cJUo3r-B&ZfqFP7;5z(64?;DZUVHGlJd z+~xyM&H(v|Gy=*5O;{tr@}yaRSE-dEd~{$yfFkiPxdDVkT2DBRmoHm36KqQT{WKY5 zg0<_8&Wh1tqLH(7b^#1r?GYaaM67aX76a5q0k$<{02DDnkO&hw0R+WbMCfpK4MfA- zl1fhPl#qC=F&iaEwAg=+C(3%-u)xdd!M2t*Ek2GlC)?!gckYO4_SJnw^9PR};RoOc;0NH3pZ~2QInmJ_y~F?j002ovPDHLkV1iepc|QOE diff --git a/companion/src/images/library/20004.png b/companion/src/images/library/20004.png index df09efa350ea2b71f341b1c4bd86b9af7c56304a..277f9071432192f8185944ca54ec237a09a6b6da 100644 GIT binary patch delta 649 zcmV;40(SlG2FL}FB#|*Gf8GKZ3OFbvFlsme00LP_L_t(&-p!dwazh~uMAa_e|H_>O zGhbjae25p>#05`{h6aOj_wzZq8E_W>*A=)7fa^IxUIhUEK^5EtKqCph0}Igo*_(u* z^#DOoL|{fJX#MV-Rv_+cmw^z-&+i%)a7%@)%_<;-9pvY964Gl5e-S_k3{*aLC=fLu zC=d>%LK(*_K!H%_m@)GyO8{;;f?k0Z0y@XI2H*(<3<98~DXawGTsNVB@KwobJ@=n{ zU!T4j!ze(kED(&*vKKvl8`EVN21q>(sT3g0+x0X2O1&k3v`&;DNUxrHbwoA71VE7o z-PCvaK&_gW017eNe@XA6$EI1(EOj=@UXOmk4~$KDnxmU^MC^~CR?)9_LfS$fSoynC zdFpOxBS6e5n7!C;1-vipnU-hw*;$5A>y9~?n@?u1$6aNYW`rL)L_WBaAT)HFnCc=#X- zj?L@CH^;H)o`gu@cTZuq48y$31ISwxqWBOB+UGE<01eWFTtx3iJqchT@OC^3p(A|O zj-Wr13AkJUgpDqa7v73%5p;vT8=x{_C@V5uS-25EF=$#%#^$Uh<0b_(6N<7iO5PrK z1L!6g^>py@+EXaKT{Be`bx+a$IhI7~XM41u14^TV{fVE-=0Lu9w z6#@?ZYKC$?B(HSpxjr2}viB;SQ{eHw6%ybiKu(bC($QZ|kv(r6PQprr`f2ev0+$`p jLOt+xM>O=g{@d{%m*Y20HW7U)00000NkvXXu0mjfV7DN+ delta 815 zcmV+~1JL})1?~orBnkm@Qb$4nuFf3kks&O9+yM_4As}M2&&&V-01|0bSad^gZEa<4 zbN~PV002lsF*!Cl$uK4$0008iNkl#O0Xh*fClQeu2nK>fDt)d3Rv2Ugqar0IO=zit#GZo0bcX>9 zrvi*q_$uh0QI#-m^ZGv%{el53_h?6=d-NQD5QEo~{a4J>c0(ZmxvnD7wZk>1 z5%yw_+*~JAFaOfYbWB`Gof@k`tQ9%U@%QZpQeMEdNGzp2t zx<;b<(F8zQNDjzu$5!~^ZU72`MGn!9??&PJblif`y2}y;w#1&_AiiLL0c!4Cgm;bl zbP5zeQ0(}q@GT=6uJ2z+1adB5en-a(vtmtxTV}Tbz&LLdifrzc8v&?)8P-gbwK$u} zxQPMFgrYBuNtVam0BjQs-5tP@gpB~4Yh>*XqagPI@C_8@Ee+P)@XZ-*tJ541ybquo z3xJxj0|5H|kQ4+QdTWNhKQym&YFyuf4>7O8IR=LL)|~(+0Z0VRE**Vy3NhX~oP>%5 tJz6{tfnPhKFZ96I9nqs2&(Gf-{{zJoiD}fLMqdB`002ovPDHLkV1lq>Urhi2 diff --git a/companion/src/images/library/30001.png b/companion/src/images/library/30001.png index a699fad9565cd54ddefe1b2f6cf9e9734ecd2ab4..936732b2e39af666f330a515317abb1350b098d8 100644 GIT binary patch delta 853 zcmV-b1FHPL7U2ev8Gi-<007d~e}4b~00eVFNmK|32nc)#WQYI&0~kp}K~#90?VQVU z!!QU%Q775u|Gzdf>Z%<#)dQi61QutNPGW?`EyBol$~k8WOp#Lh{X7#Mj-4;D^+1Jd z&`N*L*eTfx0T`kd>`@Vn{5}L=gkI3NK^?X8U|9`Rk*0Zsjep1ho7owBq7cAVb_D

Eh0JLM= zaXbjZYVe5w0$3Gz?)cUOv3q`c3<<#c$q?Z-QV>|1uhM+nx)ZoFJ6H>T4VD1BoJ@~Z z*}>C%H3i`5M1Mxn$`0P-#flI-Ah4igdCx^6Pgrx?5h zzL^06K3)RON(ckoNH-!gn68g6A5RhF;p@s_pNr*{@YsgLC5oB1KuDL!V zU|Ik~Ap%WOO7;an6e7?f=j^8sP!mDa2{L}>(~SUX6n`t*5Ji#VTv4=wkH$p}5a{84 z39yK#n@u7E98L(p5gNs92mp+?o<#`YaN;s>F|`cwd_L*@elPZBPyn;txL(s{_I4{o zx3J|SqUj{{add3%IIJZg=iFS|df!X!b8Tw-*Yai6nqLa`s86D|gpHh_WHNfk%zlrs zh4Nv=et*X37)=2n13H@_P&U0)=~sGLKq9beCy;Bbmbyn&EqN%zx__U%UN6ycvvgk@ zM};DAR7soyWyI!av54@G`@5Mmj#>h^BIMX*_W`VLvF>_7g;ltIZru!8QT(8fmyUxh z08>g$Kc-$4t8s$`vhcF_jK7zxP-0sv*z=@WW`A^EV=urV$SgQr1E7}-iM^Au38yI) zuZtf9d6~$y&pno7XND;Oa2(QZC7;g79zhBAW)OD}>CWJ6gN2hCJqt|h_V?mDf}}fh z=#*Bn*SZGw9N-qc;FsovTMHC3fV4TG@mu8a=;Cw*+T&K2fRzE2*hGyvlUlV4z>#C6 zwN3!*J%Px(Sgyy;u4_I2BsQ(E>RCwDdjjLRJ^Mr-;BZ0!hZ6!g95n&l^_u){EX@E> f0NNv#fW!F)dB(`*NdBM^00000NkvXXu0mjfz1oQN literal 2879 zcmV-F3&8Y=P)Px#0%A)?L;(MXkIcUS000SaNLh0L01FZT01FZU(%pXi00007bV*G`2iyS<7a=Nw zW+u`A000?jR9JLFZ*6U5ZgcuIskNY#0Zp(?#1JUl!y13ib4 zLi5!l!J|}G3$agiQJ+wsM+zEQKWRlx2RYch%FPwgw)%+5T2Pd1RtUwj{VV`szeuuV z-mj9JB#&yE%_bR>w9mONb@^!k*d|{sL`i;WYtg6e&%cf=`D|fo(q(`9MI!tx0A-QF z>plA1lu}b3!efwL?{PU4knrvD^Ei<9A>EUw7B#h-#>5e8(t3aKLkc-6#Mht50qWA@ zt%lrj&u#W76)q7WN!~xT=xvgIUJ9HP^5D40Vvy8BR=Zj1l13KUr&iXVmjVSzS>@u2 z!DX`Cbsgz0v1ccE8hsr4N$VOwLXNzsp0BNJV1`slVjbc@OZ zX_8c{CD|vNa;)iV^{gt%)m1fI!Zm~>*EoyLBttZ5D1<47xE99;(#RUJ4F%D64zPp5 zXV5A(8eO{T@(%QWVzWa78at%|c%c9Xj7~SYcOFovfG!GGLB*fX7Z`0v_;$OAF`Ug{ z10G}rICkd<3cBg|=W6Pl)j6Pp!%+ZeG#qR=uv4^XmPGFxwE@G}&5J<+nqZP-Kp|?0 z0$SAMtwN&@MMX{JtM$C&j62q`jvWIIS~HN87Ez&{!8+i;VFzdqZXk+Mx?Chp(xfzN zXUnUA&yC(ex@!KHnzDlf#a~l|J4m;vkU~_H0IPJ|I5su|y6pwHj{$(}81gS(XAKIA zGy^GwH-_QBo1t9yf84yd?bv_^DRhmL6%=(wykTIYasX{maM(AfK%+pXbP136A9Zq*+{=(Sb^JaLk7R)+xACF)*{?b|yfBM&RG~t&xK848dpkIte|hF6J@0GwHaDECGoi zsZC+O%A-e(P+msHG9g^HlJg(8!~-0r2deB@aO!M|_sxN#wIkM;0My>RkVJ6-+gX zKSEGeDTLs8#FlB%40)AF+U4>?UFzz@U@^-i?}U*Rgn|rdh$czO@|Yx3*jG2yW0bm7 zhK3~X!ek~?L8wU~Ttk?ZJq|q4XMK^}3Uvc^YNLUmn)!orD&ae9W6;i~R;|LW^>ofs zRLD|tHFy}KzvDZjvO|FaHwDd-76o07Njm=fFowP~9d@7$s~ZL=X@dcSH$xg!<0;DT zr$L#;A!%aOO_CPoFjEKg0zMdY8xW;ck}k?A!?YS8hnRnBmnps;S#MYNG~10$uM^q^Z&>`;LO(f3efdzsi*5w8Dp8IKuQm*AOH| zllIG5;z;2L5rc7(c}szA>`y0r_E_Wbv}Mv~1iXcdPD(3jVZbo3cax?h!3O@J7p_`C zav_({B+beQVS!m*3Mro=Alk{l={OOI~e?L;efjR63D&U6)1&O9KL)mbL z%~6W_NWq6*q^?OxRoXjRieeW@R}mz%Qa1Dg4WnB-2e704T>uJvHY!Jh-Nbl<0gX49 zrK3T8(m09VNcf=_H|e%#fLW#$p+)(S5LeZ*W>E$>W^@LWXGWg^=(d3~&H+_tzv*B! zqxFK&gu{l-2U3%3Wx`C4zN3tFd_}@|Fzeh;y~S&1PY^zoqb61{~!X7bFO`G43reMK|4#LLxDyW z6*e$8`hdg`%b{!SD93+b)b~aJ8tm{Hno=h$hQrx#&7jt-t285@+y1J|0WEd^ z|3_fQ3Jhm7aC(30Lv2_+n~32!RkLQzN=IG`j2uq~Vbsg_ham8s2aSEQq&`V~()e^p z*Uh8KYRMGVw~P8DkB^sczq0x6v(BlIbu4r25h6mE|vY`Hc2YMEg_8fwD^XSHd8D`{DL? zN8s_&Cs`UkKj%e-xQ4&P5c{Ixv(s1KUVmN+)Ti?R%RTkm2nZW7CXdqNl3Gft%XzZ% zjhENox!xze$#V#Qn$m4B*pwEfJ*wDC*PQ5!c7>l80X+2y$z!l26g*nA6bLG7U9{ai de8)xe{{c=w3LCSt&@uo3002ovPDHLkV1hP@M>GHc diff --git a/companion/src/images/library/300011.png b/companion/src/images/library/300011.png new file mode 100644 index 0000000000000000000000000000000000000000..dab44fe5f5476ad5f7b5d32372be65aff370caeb GIT binary patch literal 2821 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 diff --git a/companion/src/images/library/30003.png b/companion/src/images/library/30003.png deleted file mode 100644 index fe4548967cd1905da62af4e5de165466da0963e3..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 4233 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 diff --git a/companion/src/images/library/30004.png b/companion/src/images/library/30004.png deleted file mode 100644 index 4db2f79bb9cb87fcf9e811738b3ca3f53f2c7170..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 3049 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 diff --git a/companion/src/images/library/30005.png b/companion/src/images/library/30005.png index ceeb0b358f1fac044d80d38649490942d28ce0bf..8761d4fcb984cb975b78e7d3febab2bff3719b8b 100644 GIT binary patch delta 2346 zcmV+_3Dx${7~2w%B#|*Gf8GKZ3Mefen2hEC00`_!L_t(o!?l^&mK!;eM9qQN$Yf@9 z&CHqq|Gw_(R+Y$Du(;oOprlN-YE+_H0$+F{c;H6!%^WcFbCxHQ=RT+#LzwAU%B(t? zB-wPG+NemkOZrLnmGL7hsSbI#C6hSjX3vX_mP~&?+o)?=FS4J-e?T83JSIs}8GAol zHgAI`!x&p1B+uG^8UraLv#Cj4`qF6D$CCUkajlLfK0!d>G!AK zS4{Q#@-HsMr-)<7*V%ra3p8Axb-QS4LY_sU4~F$@*NcuZtISgTGzNyjFRCwQ4(q5% zJ83XrHZIziOq;dof9Ej}KAsLu#lj4g*(kHoPO&XI7EJ3?m`UHkK!g-7siXe-v`8xI z3c0RQo|Z!t(V^MgF&oHJi$z*w(vyrhh3dNzxtP;#02 zWHuHXbWGWNwSV95VHbFo)W&TbRVUTy-qPLkUggF4p7FwYn%j6F}uYK&^b7Ysb?f>eGTJm$hE8?jIJ zIi_ATWVhkU)KiEX>h)&9<;9|B-DK9k^y#DP=%eXL2KYZHA0KzobCT$WBA^jC8#V8;LItPO58nO90Kf&37HQV2ec8H% zMfZlv6zU^l+LCZ8l^}rQi`^a!!ej9qmS~qAQfA)ks5+5^u|CO|-``%=cLW9dU5{$k4qV<5Qw(gstR zM?2;&?pxS;78dk#wIumq5!*$#%U{}mun=MS7mcQtwYFib$f{7`<*+)ZX+CleOAE25 zMY{B%fBaYg>Ks*C$H7m_ZCkd?ENhqO3zYCSK^|hGoZ7(3u+RFjE>NU8VLr$$d0IB5 zI?1zf|H#yHouo2*mfHA(V<3{GIwisq7@iG_L}iu_{nUoGoiSmazqPkKD0O4=i^VU= z3j>z_&W0T}EpGXEYPt9GJL#%5e|ub2;Goi-f6e2yRvun)fYkx+ZKv`qP!oy6y}#^Z zhyp}1)Lexg_ulkvO9TgO1Z;0#G~fvL8yj$Q2%;vdr*$Gx*C<>XO`M;p!;jUF2AHVEt86z2~QMKz;M~=+Z@;x^lS#?4N1DsLmf> zQAF<{AUa*T1mLyL3_*x+M}H`ij1Sofz90DKm9Ni|;FwsWM|1W!4Bw#h6$ZQm-kVHz=-PwD27Lxj1mX*(SeUJE>CT!G$^(mo!tN?vS zo^EtFuzTJ+PU8q5{Qs#i_h3{Fr@vx2DDhUF|49rK&>(l{OA(5(LeFjJLK-@BaKP#Q zC$r86Pj{3wg8h4El1`dG*_D5=*`dMi1fvoN?W_blw7k)9vpXb_B78q%OvGZdDuBOLAXQ5 zm0W_UadXgC0a^u(+JLh9V{@G25J!8F79`VfUe&eFJRuu&*y(q4>)a?EjfgULMHRU~ zJyju=4+3M~9}!v~f4emr*XfsC2-7H(7`2+v{50S0!`z)>(Imn-f5jgN-FJ{$`%p`w z_eWx&!rJd&T#F_oScHUz#q(6Q0*HbmG_;&Lo7fs6K&WNWA=vS9&;18hH0Zrj!L!h8 zQbAxF+SMmL&cK zH>zWiFlp$<&^#wk$~_X+#v|u9lbdI?a`~>CgFYX*Wz{@ke|@y6aN72h+F+5Y2E}q&}&$HCUmkX2hZ_IL;Cr?Jgl>{hap>>+u}` zaz-@R4HUA_`3f7&9bXXw?uW>yod{rM$7$?u?Kk3hs1kl8U^omRtRY5qsFWZes5GOW z8#&JFkG`?Mf83HR?XxgsNNxIZUP*OWCv)EY@GBEjN?SBdhB2-&wzQ!4e{w=XS-1~Y zKbV1<^L94U@m$`&$kYbxPjY0l#Xk&IKNdin4xQimVy)PVWnysK{_KpXmnZ%9KR@Bx zD$z&j_WX3SsT@lj=lg}~=KwrueR{ol`H^cotGC5eAZLz6w~OlZ<)PXC0XtA(h?7Mt QL;wH)07*qoM6N<$g7dJ1kpKVy delta 3107 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 WVEP`H9_`Nn0000#%MB From 575ea504aa7aa14798f48098836eab852031b018 Mon Sep 17 00:00:00 2001 From: Kjell Kernen Date: Mon, 24 Feb 2014 14:28:19 +0100 Subject: [PATCH 60/89] Updated QT resource file with new image names --- companion/src/companion.qrc | 156 ++++++++++-------------------------- 1 file changed, 41 insertions(+), 115 deletions(-) diff --git a/companion/src/companion.qrc b/companion/src/companion.qrc index 1c4550d1a..c6246f314 100644 --- a/companion/src/companion.qrc +++ b/companion/src/companion.qrc @@ -168,131 +168,57 @@ images/library/00009.png images/library/00010.png images/library/00011.png - images/library/00012.png images/library/00013.png images/library/00014.png images/library/00015.png images/library/00016.png - images/library/01001.png - images/library/01002.png - images/library/01003.png - images/library/01004.png - images/library/01005.png - images/library/01006.png - images/library/01007.png - images/library/01008.png + images/library/00017.png + images/library/00018.png + images/library/00019.png + images/library/00020.png + images/library/00021.png + images/library/00022.png + images/library/00023.png + images/library/00024.png + images/library/00051.png + images/library/00100.png + images/library/00101.png + images/library/00102.png + images/library/00103.png + images/library/00104.png + images/library/00105.png + images/library/00106.png + images/library/00201.png + images/library/00202.png + images/library/00203.png + images/library/00204.png + images/library/00301.png + images/library/00302.png + images/library/00303.png + images/library/00304.png + images/library/00401.png + images/library/00402.png + images/library/00403.png + images/library/00404.png + images/library/00501.png images/library/10001.png images/library/10002.png images/library/10003.png - images/library/10004.png - images/library/10005.png - images/library/10006.png - images/library/10007.png - images/library/10008.png - images/library/10009.png - images/library/10010.png - images/library/10011.png - images/library/10012.png - images/library/10013.png - images/library/10014.png - images/library/10015.png - images/library/10016.png - images/library/10017.png - images/library/10018.png - images/library/10019.png - images/library/10020.png - images/library/10021.png - images/library/10022.png - images/library/10023.png - images/library/10024.png - images/library/10033.png - images/library/10034.png - images/library/10035.png - images/library/10036.png - images/library/10049.png - images/library/10050.png - images/library/10051.png - images/library/10052.png - images/library/10037.png - images/library/10038.png - images/library/10039.png - images/library/10040.png - images/library/10053.png - images/library/10054.png - images/library/10055.png - images/library/10056.png - images/library/10025.png - images/library/10026.png - images/library/10027.png - images/library/10028.png - images/library/10029.png - images/library/10030.png - images/library/10031.png - images/library/10032.png - images/library/10041.png - images/library/10042.png - images/library/10043.png - images/library/10044.png - images/library/10057.png - images/library/10058.png - images/library/10059.png - images/library/10060.png - images/library/10045.png - images/library/10046.png - images/library/10047.png - images/library/10048.png - images/library/10061.png - images/library/10062.png - images/library/10063.png - images/library/10064.png - images/library/10065.png - images/library/10066.png - images/library/10067.png - images/library/10068.png - images/library/10081.png - images/library/10082.png - images/library/10083.png - images/library/10084.png - images/library/10069.png - images/library/10070.png - images/library/10071.png - images/library/10072.png - images/library/10085.png - images/library/10086.png - images/library/10087.png - images/library/10088.png - images/library/10073.png - images/library/10074.png - images/library/10075.png - images/library/10076.png - images/library/10089.png - images/library/10090.png - images/library/10091.png - images/library/10092.png - images/library/10077.png - images/library/10078.png - images/library/10079.png - images/library/10080.png - images/library/10093.png - images/library/10094.png - images/library/10095.png - images/library/10096.png - images/library/10097.png - images/library/10098.png - images/library/10099.png - images/library/10100.png images/library/10101.png images/library/10102.png images/library/10103.png - images/library/10104.png - images/library/20001.png - images/library/20002.png - images/library/20003.png - images/library/20004.png - images/library/30001.png - images/library/30002.png - images/library/30003.png - images/library/30004.png + images/library/10501.png + images/library/10502.png + images/library/10503.png + images/library/10504.png + images/library/10505.png + images/library/10506.png + images/library/10508.png + images/library/10601.png + images/library/10701.png + images/library/10702.png + images/library/10801.png + images/library/10802.png themes/monochrome/16/paintbrush.png themes/monochrome/16/open.png themes/monochrome/16/edit.png From 91f8157f033c6df10ece8fc16bafdca29d97d2c1 Mon Sep 17 00:00:00 2001 From: Kjell Kernen Date: Mon, 24 Feb 2014 14:41:05 +0100 Subject: [PATCH 61/89] Renaming files to change order --- companion/src/images/library/00001.png | Bin 353 -> 2331 bytes companion/src/images/library/00002.png | Bin 2331 -> 4365 bytes companion/src/images/library/00003.png | Bin 764 -> 2971 bytes companion/src/images/library/00004.png | Bin 0 -> 7521 bytes companion/src/images/library/00005.png | Bin 451 -> 209 bytes companion/src/images/library/00006.png | Bin 3469 -> 209 bytes companion/src/images/library/00007.png | Bin 3760 -> 209 bytes companion/src/images/library/00008.png | Bin 3485 -> 209 bytes companion/src/images/library/00009.png | Bin 4665 -> 209 bytes companion/src/images/library/00010.png | Bin 3727 -> 353 bytes companion/src/images/library/00012.png | Bin 3151 -> 3469 bytes companion/src/images/library/00018.png | Bin 0 -> 3760 bytes companion/src/images/library/00019.png | Bin 0 -> 451 bytes companion/src/images/library/00020.png | Bin 0 -> 764 bytes companion/src/images/library/00021.png | Bin 0 -> 3151 bytes companion/src/images/library/00022.png | Bin 0 -> 3485 bytes companion/src/images/library/00023.png | Bin 0 -> 4665 bytes companion/src/images/library/00024.png | Bin 0 -> 3727 bytes companion/src/images/library/00031.png | Bin 0 -> 1040 bytes .../images/library/{10104.png => 00051.png} | Bin companion/src/images/library/00100.png | Bin 0 -> 2294 bytes .../images/library/{20004.png => 00101.png} | Bin .../images/library/{20001.png => 00102.png} | Bin .../images/library/{20002.png => 00103.png} | Bin .../images/library/{20003.png => 00104.png} | Bin .../images/library/{10030.png => 00105.png} | Bin .../images/library/{10031.png => 00106.png} | Bin companion/src/images/library/00201.png | Bin 0 -> 1654 bytes .../images/library/{10011.png => 00202.png} | Bin .../images/library/{10007.png => 00203.png} | Bin .../images/library/{10015.png => 00204.png} | Bin .../images/library/{10094.png => 00301.png} | Bin .../images/library/{10096.png => 00302.png} | Bin .../images/library/{10070.png => 00303.png} | Bin .../images/library/{30001.png => 00304.png} | Bin companion/src/images/library/00401.png | Bin 0 -> 1627 bytes .../images/library/{10036.png => 00402.png} | Bin .../images/library/{10038.png => 00403.png} | Bin .../images/library/{10039.png => 00404.png} | Bin companion/src/images/library/00501.png | Bin 682 -> 863 bytes .../images/library/{00601.png => 10001.png} | Bin .../images/library/{00602.png => 10002.png} | Bin .../images/library/{00603.png => 10003.png} | Bin companion/src/images/library/10058.png | Bin 337 -> 0 bytes companion/src/images/library/10098.png | Bin 863 -> 0 bytes .../images/library/{10085.png => 10101.png} | Bin .../images/library/{10088.png => 10102.png} | Bin .../images/library/{10090.png => 10103.png} | Bin companion/src/images/library/10501.png | Bin 0 -> 682 bytes .../images/library/{00502.png => 10502.png} | Bin .../images/library/{00503.png => 10503.png} | Bin .../images/library/{00504.png => 10504.png} | Bin .../images/library/{00505.png => 10505.png} | Bin .../images/library/{00506.png => 10506.png} | Bin .../images/library/{00508.png => 10508.png} | Bin .../images/library/{10083.png => 10601.png} | Bin .../images/library/{10092.png => 10701.png} | Bin .../images/library/{10093.png => 10702.png} | Bin .../images/library/{10026.png => 10801.png} | Bin .../images/library/{10027.png => 10802.png} | Bin companion/src/images/library/300011.png | Bin 2821 -> 0 bytes companion/src/images/library/30002.png | Bin 3381 -> 0 bytes companion/src/images/library/30005.png | Bin 2395 -> 0 bytes 63 files changed, 0 insertions(+), 0 deletions(-) create mode 100644 companion/src/images/library/00004.png create mode 100644 companion/src/images/library/00018.png create mode 100644 companion/src/images/library/00019.png create mode 100644 companion/src/images/library/00020.png create mode 100644 companion/src/images/library/00021.png create mode 100644 companion/src/images/library/00022.png create mode 100644 companion/src/images/library/00023.png create mode 100644 companion/src/images/library/00024.png create mode 100644 companion/src/images/library/00031.png rename companion/src/images/library/{10104.png => 00051.png} (100%) create mode 100644 companion/src/images/library/00100.png rename companion/src/images/library/{20004.png => 00101.png} (100%) rename companion/src/images/library/{20001.png => 00102.png} (100%) rename companion/src/images/library/{20002.png => 00103.png} (100%) rename companion/src/images/library/{20003.png => 00104.png} (100%) rename companion/src/images/library/{10030.png => 00105.png} (100%) rename companion/src/images/library/{10031.png => 00106.png} (100%) create mode 100644 companion/src/images/library/00201.png rename companion/src/images/library/{10011.png => 00202.png} (100%) rename companion/src/images/library/{10007.png => 00203.png} (100%) rename companion/src/images/library/{10015.png => 00204.png} (100%) rename companion/src/images/library/{10094.png => 00301.png} (100%) rename companion/src/images/library/{10096.png => 00302.png} (100%) rename companion/src/images/library/{10070.png => 00303.png} (100%) rename companion/src/images/library/{30001.png => 00304.png} (100%) create mode 100644 companion/src/images/library/00401.png rename companion/src/images/library/{10036.png => 00402.png} (100%) rename companion/src/images/library/{10038.png => 00403.png} (100%) rename companion/src/images/library/{10039.png => 00404.png} (100%) rename companion/src/images/library/{00601.png => 10001.png} (100%) rename companion/src/images/library/{00602.png => 10002.png} (100%) rename companion/src/images/library/{00603.png => 10003.png} (100%) delete mode 100644 companion/src/images/library/10058.png delete mode 100644 companion/src/images/library/10098.png rename companion/src/images/library/{10085.png => 10101.png} (100%) rename companion/src/images/library/{10088.png => 10102.png} (100%) rename companion/src/images/library/{10090.png => 10103.png} (100%) create mode 100644 companion/src/images/library/10501.png rename companion/src/images/library/{00502.png => 10502.png} (100%) rename companion/src/images/library/{00503.png => 10503.png} (100%) rename companion/src/images/library/{00504.png => 10504.png} (100%) rename companion/src/images/library/{00505.png => 10505.png} (100%) rename companion/src/images/library/{00506.png => 10506.png} (100%) rename companion/src/images/library/{00508.png => 10508.png} (100%) rename companion/src/images/library/{10083.png => 10601.png} (100%) rename companion/src/images/library/{10092.png => 10701.png} (100%) rename companion/src/images/library/{10093.png => 10702.png} (100%) rename companion/src/images/library/{10026.png => 10801.png} (100%) rename companion/src/images/library/{10027.png => 10802.png} (100%) delete mode 100644 companion/src/images/library/300011.png delete mode 100644 companion/src/images/library/30002.png delete mode 100644 companion/src/images/library/30005.png diff --git a/companion/src/images/library/00001.png b/companion/src/images/library/00001.png index 0218d0570a6be5207e3bba6c272d9f3c45af1b6d..43cd387dc7b790ab437796d6464fd402a305adfa 100644 GIT binary patch literal 2331 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 literal 353 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 delta 2294 zcmZvedpOhm8^=deB1Ds#sXYuM=TuH9eul|ua{4AEkyA*qw9<-75jo_zP&{p!GqoIZ z%BE*BQPZ&GxHOw(W=TDMd!DP`f4@KP&vjq-=lZwQH>t|Y?w($GAp-)*63`BI-ic$pM{eOe+;-76 zRL?$rkq3F9W;gNUrjy&%9S-RBFMYl9z!q%q_>i{XU@RW zG;`h{9334WbFJb7Y5o1OlF|VKro~ZysG#t1wH-dYckMcAR&)z4JMe08Wq;?#7Nt^7 z^x;$>00WT+t8Uw@(GdmYYaA(HYtok|#9(Qufq?-?^riWM-Sl;KbDS2HN=;iGVY35Q z z?8!KYH4HH;a)56~-XjpnSVyzs z4S}{tp=6pMz2q97b}dvA!C8=TGw2T7=AJ6ugxpE!76r#PhCe$4)Jsbt-?o59| zCd)PWZzCLvJ;zjs!CwDb7atZ~(^i8-&3lkWC?}C9Oku67Ud>-F+7T1($V5}2_=hMe zJ|V%hE|%3OQ&UsZd|^tuX;AXmxF0JKv%<9(hDhf9B4@;TaW}c`A*(P{H4QMb+m1Ie zG4b@AH;%MQIN+z*`{e@yWw5iCix`29KXe-^kLAN$oE?| zyVboZ)P}J?SE~=)7dO#3p@+_Koq=iP@qK%GoBc{T8XYrv=WsYE$-SgUATVLp8N=@Q z2IE9uRZDHIOrwp@zU9pkI^DF3@UCX;CtllLIU|Ch#;qkThja*D2L9H6|G zThC3$5YG1tCJy!M2+h&h(YkKfE#LBPr%PQ}G z+C87RC0%7y6-yHPohPIdkZHk@3Y%`;;3W>cX=*vJ(0rR62muKeS^L}Z*Vcwd_ISRL z=__6>dJUP^bcsx`9uAty^i?vsxb<2wk(G9JpxWag!H^p?Vy=+w9D)*Whc2#r4ix6( zq^VTbDy913h0k45uV>-{5|lKoZuuL`vnJ~ejLJ-(0ZrNrq5R*T78^>b2By3DW06i6 zh~IQqUrfDUV22yw;8b6_+Q<4cDZGOk8X6xv@kfAXeMcG_@TPe(3?W4g@z!9>Me?Ed zTQ)wlhtD zIrO~a-_7IG^r)FJO^vXL0W;!A1cU0P>rv_;ksKi|EKFC(NM2v%^>$np_s<2mB2)n8 z=WIkJK3wJOi`MJ(gpo#8HJ4uzU~X>iU;4|$(()dkAG5N$YQ}wZ1iy!tsi9?8q)6fvS)VkB1g(4gd zSD(Q3Re8ud50$$;G&BT4=g2jBIR+V`RiJn%bi3Sb8|(Gf+sYn>GRCBSYisLw@87>} z|9g(EW|JrYfdn%&rFbmXjLRGytss$Tml)5E1MEHvk#m0N$Zx4J-3>?QG4FHcof)gKZ8Fj%Kc#&YBo6%|iV7!u{@{KzAF?;`7K zpITS%j=WztPb-Acx|hUlP(LGEsmrF=!4i{ZoG9{LQldwh?F*a3l*-DjlIcx9KPB2^ za!2b5L@)KyA3I?F6gC&&?TiWn>R0E*>wzBj&Dzf-fFSqCxgl0E7`@xPzm^ew5{Jal=AvsgMZ>*7sj<0E(D!= zshE_Ml)t4d>+xNmV}5>WSl(DDz>(Zf@i2m_tMB`2#sAoFrgs@sh##I4j=l4(`oPm_ zcLF57zM((6{IA#lHuwK|y(9qq&I7*#z(0B5cTaiN253C?#81wR%ScI-0ijXu4z>0{ G$^Qkmv~u?V diff --git a/companion/src/images/library/00003.png b/companion/src/images/library/00003.png index 9f3c5d78e040bf7ea81c74d87f2edabced38ae62..a179deadfdc73cbebacd24e1dc58b38a9ba9eb25 100644 GIT binary patch literal 2971 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 RR#E@}002ovPDHLkV1mg7tjqua literal 764 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 YrWpxnLoMrrGgAmoK~4URtXbgy0Hqy2mjD0& literal 0 HcmV?d00001 diff --git a/companion/src/images/library/00005.png b/companion/src/images/library/00005.png index 6d5a1d93d4cad3c168a2a5f0f46cd67c9786d9f5..802e9885a8d41bc2573134d0c875e5e07a120834 100644 GIT binary patch literal 209 zcmeAS@N?(olHy`uVBq!ia0vp^SAf`o14uBqJF!g!Qk(@Ik;M!Q+`=Ht$S`Y;1W=H@ z#M9T6{T`D94;$Owbqp3jA<+`oh!W@g+}zZ>5{8h(qQtz+Vg=9K#Pn2YAJaCV0)I~z z$B>MBZ_hLGGB9v3FUbCXZhLz(o6qO-ZeFAVE%r(G8SAxEHyZ+tX7F_Nb6Mw<&;$V7 C>o;ov literal 451 zcmV;!0X+VRP)M?s9>M``&~-il000McNliru-2?~@A}>_EeGLEr0Z>Uq zK~y-)t&%ZL!$1&4*K*+oVdxRLM%*M6T!A`g2u)-O;oN{43B@hq3N+i&;1eK+3m_*V zB$ga6e>~1=$4-O9uSQQVKeM}5>Yp+&O^UyO<$a)sr33WHm*C-Yn(bl-q>EUB@q3(= zkpNR2N#N_~QGg&T-vme`NEZN~Vvi2cqeMq5ah48nPy2$T4AwOFjc24a3Yw31JSlY& z7=3FyE|fa;&0H9vXS}s*gsS$WF|U0#u8>I;8hsZOH1nna%VFqj%D_1bKyfx;;~Jrk zof?1BYz+W5&JpUURI;Mk8nrUA!+1t^0I+d`O!y}onyrCSY2a_AVfQ!~SX~!;$ zU_-Mta6xR$5bD4cZfUlLz4b!}fas|4P;Ahn!l>|+Gn)I~$9`|}oWV9n`bN{y8pk_& t#uw6pADSCO^XD2g#%m|abkcOV`33v%2Zo%LoI?Nr002ovPDHLkV1j1%y88eC diff --git a/companion/src/images/library/00006.png b/companion/src/images/library/00006.png index 64eca2f6622431d42cc2fe98cc671ec54334e97b..802e9885a8d41bc2573134d0c875e5e07a120834 100644 GIT binary patch literal 209 zcmeAS@N?(olHy`uVBq!ia0vp^SAf`o14uBqJF!g!Qk(@Ik;M!Q+`=Ht$S`Y;1W=H@ z#M9T6{T`D94;$Owbqp3jA<+`oh!W@g+}zZ>5{8h(qQtz+Vg=9K#Pn2YAJaCV0)I~z z$B>MBZ_hLGGB9v3FUbCXZhLz(o6qO-ZeFAVE%r(G8SAxEHyZ+tX7F_Nb6Mw<&;$V7 C>o;ov literal 3469 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`!2~2@x4h5*Qf*Zs5hX#1CLR`=Ysy8gRJ$k9D1HV7KUGkyqwI>m8@}dqp{&Z|7^4S@O9&ev2rN zV)n(_9m*RMoxkzO3bRHW*jns2Z|xkA1@fA+rNF$_uczjRP5ndetVU-MOv$` z`UFM>=J%*p$~V}1On zC3`zAn+hwS0lBFqi3%0DIeEoa6}C!XbFF}Ekg&dz0$52&wyjcxZ-9bxeo?A|iJpm` zfv#&sW|@(a9hZVlQA(Oskc%7C2q4c^DWjyMz)D}gyu4hm+*mKaC|%#s($Z4jz)0W7 zNEfI=x41H|B(Xv_uUHvm1jG!N)Z*l#%z~24{5%DanTbjHr6smXNP z3=ITeaOi_%^bPe4^pTa9WTxRz4w6AA2Whqn$gD`siEzoxP0cF?I>A=S(8vO87(zA@ zN!H8+ED18m$}=}HJvBTtr6dEW3r*M~H8VW}=nbHHeNbrWLxT$#`ugzT2ZaIc!Kfu9 zh4E-`jRqGTqK16Ns32P*U$(!%{4%=Ohe9m%cXFEE{NwI@_$E&K--4*9s zRxL1MGoKmfqi1$?Y2>xpA4?y}MsAH;duUfw?+2OOgI@XuEuD{wxmO?#~Z5CC-UzwmK!ps??>sbwl>aEW4!)Yp2?VUc7Yc z6NkL{Evwr8dgW(R|2eJR$PqdBb2#6+m@bxulNyY2?xwC#(%o|Jwm64a{_mIEl||e3 zNKaW9ohhdx7@F@Kw_HR0msCNOapkWzZKsPlr-azIyQugw-<+hhYVAyK8IOky>~?D( zF0DS_`a56i(BIz8Uf&d+exG>Q!aLf)@sCEq{fEL^-f;ImPCD>};ndkMUJjw0bI%#G z!khY1U5bi1_8Ri#wU*y_dQ?bYiTl!`&GC)iQ(p?P+ed0dZ8c_$i@s-+D(sl=vVXsW z3df(|fcV*Lu2(k*xm;$JV`bVmakNrEbpqyAOD_jerbdfXXdH0f8LW> zk1vcnzQ_56vfc4&X2w@x-XZ*QjsH$bCCuFV(Es*-e(_HqQ*J-W-r&AW;a29KbXk=K hmJ7(q&+O(u20lU0^PNAp%mk)u22WQ%mvv4FO#qlUGS2`2 diff --git a/companion/src/images/library/00007.png b/companion/src/images/library/00007.png index fa384d1e69d6717e7dc37c1f73537364befb0c16..802e9885a8d41bc2573134d0c875e5e07a120834 100644 GIT binary patch literal 209 zcmeAS@N?(olHy`uVBq!ia0vp^SAf`o14uBqJF!g!Qk(@Ik;M!Q+`=Ht$S`Y;1W=H@ z#M9T6{T`D94;$Owbqp3jA<+`oh!W@g+}zZ>5{8h(qQtz+Vg=9K#Pn2YAJaCV0)I~z z$B>MBZ_hLGGB9v3FUbCXZhLz(o6qO-ZeFAVE%r(G8SAxEHyZ+tX7F_Nb6Mw<&;$V7 C>o;ov literal 3760 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`!2~2@x4h5*Qf*Zs5hX#1CLR`=Ysy8gRJ$k9D1HV7KUGkyqwI>m8@}dqp{&Z|7^4S@O9&ev2rN zV)n(_9m*RMoxkzO3bRHW*jns2Z|xkA1@fA+rNF$_uczjRP5ndetVU-MOv$` z`UFM>=J%*p$~V}1On zC3`zAn+hwS0lBFqi3%0DIeEoa6}C!XbFF}Ekg&dz0$52&wyjcxZ-9bxeo?A|iJpm` zfv#&sW|@(a9hZVlQA(Oskc%7C2q4c^DWjyMz)D}gyu4hm+*mKaC|%#s($Z4jz)0W7 zNEfI=x41H|B(Xv_uUHvm1jG!N)Z*l#%z~24{5%DanTbjHr6smXNP z3=ITeaOi_%^bPe4^pTa9WTxRz4w6AA2Whqn$gD`siEzoxP0cF?I>A=S(8vO87(zA@ zN!H8+ED18m$}=}HJvBTtr6dEW3r*M~H8VW}=nbHHeNbrWLxT$#`ugzT2ZaIc!Kfu9 zh4E-`jRqGTqK16Ns32P*U$utUq8EKqtpj-^DjP|2ULIUp84hv*;z?pGpR!aK%+GE5bcqtFKbOWH&3+i!rr9 z=1kb-Lhf~%^Zi1)FPvt&Vsq$iLuCDqju%VLaP_kK%s)E6Bc`|HhxmDpBYbVzHEFu1 z^y?<*)*pN+r*Q7Y;*;CT1rJo?A4_lKu6*?T@Ypf6_cUv!Y)5 zKy9Sj8~4uH=fW=b@s+V{U2wl6{0}qBh4}?53jg+Rwbjhgp7i@S*Mh{P*jveUIbi_~ zkFMyx{3A9wC(!Ei+f&-DE59}c$-hsXXl3)(!DVN}?)~8z0lOn_u6M}QzEYp%xc%n6 z-N(;g2tVt>6m4^C=Tpt9Ccmw0A1}zPDg3=y+mKJ-y?w~?BR20p7zGwMo(y8>Vp5MN z4>tc}6so*oM+&R2oYaMYG|fp(H9vV(Sw8NN{IA5*UU5wC>g{*EMSoR8ooDuk%~$^u z^L*d&+Xo)b`dK3U%u;Es@STP3lfK8jdNYGZ`3u9w?N5!~YGnmy+?zTp{Xu;n_?o?bCe^KC4Rt~2zzdPHPd!IInRmZjVF9j(>&t2{8#g5O}{jvoalY+~cv zmD^_cv48(+J^fz6k@p7myx-?{EohTc^O|vR`DM)mNk67{%0}=Ch5k^|G#B~vE9|#v zG1tr5?(cKz($c*>chCJ+fBMIZfW5zG<>n|d2(R6~Y8H$3L9y@5-}sCF_Wj>2FHkF1 zSp93a;ic=xohn_c4o->BRGlVoAM>T9?s`bLUD&ZbhEwjTNCa^)6|Cf$v#I`H+RtCz zuQP*^v>VpEUU^tPGilq2S(nP*`EHmvX^HgqzWFnhCY`+Q`A+`eFLA$}S5E}7iU+cZ zXq9~bWv=V$lOJmvIBQP8UXDlV{2Lftf9%K&uiMbOFOoa!UgZ17cl2<5{8h(qQtz+Vg=9K#Pn2YAJaCV0)I~z z$B>MBZ_hLGGB9v3FUbCXZhLz(o6qO-ZeFAVE%r(G8SAxEHyZ+tX7F_Nb6Mw<&;$V7 C>o;ov literal 3485 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`!2~2@x4h5*Qf*Zs5hX#1CLR`=Ysy8gRJ$k9D1HV7KUGkyqwI>m8@}dqp{&Z|7^4S@O9&ev2rN zV)n(_9m*RMoxkzO3bRHW*jns2Z|xkA1@fA+rNF$_uczjRP5ndetVU-MOv$` z`UFM>=J%*p$~V}1On zC3`zAn+hwS0lBFqi3%0DIeEoa6}C!XbFF}Ekg&dz0$52&wyjcxZ-9bxeo?A|iJpm` zfv#&sW|@(a9hZVlQA(Oskc%7C2q4c^DWjyMz)D}gyu4hm+*mKaC|%#s($Z4jz)0W7 zNEfI=x41H|B(Xv_uUHvm1jG!N)Z*l#%z~24{5%DanTbjHr6smXNP z3=ITeaOi_%^bPe4^pTa9WTxRz4w6AA2Whqn$gD`siEzoxP0cF?I>A=S(8vO87(zA@ zN!H8+ED18m$}=}HJvBTtr6dEW3r*M~H8VW}=nbHHeNbrWLxT$#`ugzT2ZaIc!Kfu9 zh4E-`jRqGTqK16Ns32P*U$qaB~dlF31b%G-9GvJKIn z!zg;uzNpg9nS*o7nnPQ}9_Pz16c^flp3RcY=2D~7ui_W4@~f&&B;Q=#l&OAal9YXPdxjBi%9pNsypr{Bs4eophB~6Hs|+iif?Dcu3(Q4O?hJ=%wVxI z>ql|R)1wm`CHP;ox_b&r@Mzw9!~DT7rtaSeqf86=qcmYSP?t}%C`))jc z*s!ijn7zj~;rQBDX_uJ*w7P@Qzjq1aifd~gc7M+`U&|1%b@q=%@@;bj z&aL~W!()=|T-a;k|5sGCuYFso+<}5~0&Vlw&RcYCyUhCwDLkR>=@MLNH_Vld{eQST zUcKwqPJ`I!`}G@YBp4$9X3E`|Sf@SZ<(!APGZ`2AU+GYlu85aSYwG*Vvd1iXo?Y<7 zgC~@01sS+Q8gBRa8f05e{mo%|^DVQfr&1E)@<(j{1wIz8VXKIKH&NAjKPB89w=GfzV(fr=l#k{znt?=g8DF?u6{1- HoD!M5{8h(qQtz+Vg=9K#Pn2YAJaCV0)I~z z$B>MBZ_hLGGB9v3FUbCXZhLz(o6qO-ZeFAVE%r(G8SAxEHyZ+tX7F_Nb6Mw<&;$V7 C>o;ov literal 4665 zcmeI0Sx^(%9>yD#EwYK=5QinkK@chI`c+0?=%wT=Uq=XE~xN^#7L|=(-{{IqtU4ZQZNW(M$kYQ$RZH{ zfHiR{%?ol5C2acfwAmGuLE(M6HK{To7+ zMdkMixOX-&?0>G#wQ{vnJ-)HP=auw!4Qbc5DYO6ipoHNM%XHPsN48ELPSjMT2*tQ_ zXE$3<#u$wsh4ytso&W%mmn2?A?sm2qe<~S)!&Ci01dB}Ll?niQhAbM+KL}*P{J;Pb zMIZk9W(OQb!t2A`wCqrJG!u|WvW%pIE|KllS`XeZ*|8Kxk^pH8AN zNmL4KCllvK4Q1-X;XEDoIedryU+EOaX9zqT$Q=c#jzA&*ZfBAR|HZzee6jB=#yFB# zV6eL>i40O0yb|=`>KZzq!oH{;e^a$JKZ!d*7%MU^0CXeanMB^I|CqJ}NdZLOXYl;U z9a_lGxOnuDf8pO@@V`I4z2vJHf5Y_+*H;nvD)YD9^$pio5%?R;-JnwkV|f4q_-6iD~Z zh%8^0)xp{+gmnqd{#cwnma(d1K-a%M)OI3DPvI9%yN|bt_eaBXf4slTR7~&DO$4A@ zmw;{PcdPqa6)6UypmNVuM(A;hDv|Vaulu20Gwck-Sy74p07N)58&Dpog^t`kC znpd1VHwE(7dgXLky&;PYg?wX~+}PSclC(%OYg+YCI_4g?1hWBWlMunCV0#hjnXOj z?viS!Q^AP0^xZe@4;RPBjmwIB-P#iJW@k*T3Pq`&%8fI>O)bRBNS^e4puyHcJq31O z{wc7NsDLOIHmXrMf7VU6oBdXw(gbVL@_) zn5u1X*J)Cj2EUSsa1PgjUGq_m3mE-eTRXCH(Bu2?ighJPovgjm{*mnmg`{6gvHP5& zA3hO5%dM$w9>iX>^$@)@A8UT<2(!hNhQ@d*HBN(+FF%B$EC|5!b6byjCIk z&`zn~Ys)>p*p{{OTQLPu?#{8|`ZcxvR*6HWXGYKUJ=>M!0C9&2T$3_sIS)Dw6bHas zCt-kq!O^$QNUR}ywhlcHyyqh_!uste3j820XQroaxsLY~DBKRcyQS^er9^Bj*%Qj) z-n;z_J2E?J7D4Eda~Mu+7)Vo5-?)fUb%||>oiWTyE^mE8mvU>BL~ydDw1gmcK>ONi zjYsS3Aw14LZYs=$PhcqTl-~a7j$=edW=K>U)u5>1PC>&Sn@qU z{j*1?EGO%g8qypm_xdvb+$~vQGf!2=(DU-s{iiPDtst}Bwl%lFfgcw>mzEh4E zIcoBgbO+rmDyBiN)6g4l;>DGZ%g#`vt{%!-8gSK{xKw(p!Nk2BN{9aLDm|v1EZ`=1 z&#P3lCD2vd>S#Z#$KPnt#3`2Hs|>;1AmUFYyIt))>hF~lhx{$Eca9I$4jc$fY;m8S z2uC|S7Rp@aZ&9ke>p|3I+kfQt_qB3}6~Sj86jfFy9WK146x%HXKr87s-A|oIz0Qqz zWZVY`mZV9CpeC}FZ=Tp(^uXjLk3(z_pKX_bzx>8|Sn^IBA zm$2=qs@^Z3YZ4M%^l(gDCZH1B^r-`g7PJ(DVehPT&2sU*TGsuDMx5+S#ZT$Zfi!?N z74(3AOHdZvosy`==@_U=QbS2L;v4x&C+aqSmDqN5nj(!K-DEVRpp}mxJ{&k>tKLoa zllj$WFzKB{Rx{ou=pLFVZraYQowU-MmD5!NV!m-nPKigt~xtI(lR3t+y@aRth=#u&b= XwlJGfv{%5+{}n4Ud(#?Y-?)DPb8?TN diff --git a/companion/src/images/library/00010.png b/companion/src/images/library/00010.png index 2b2081c886fb7876f9221ab4d9f8fcc9cf3ca492..0218d0570a6be5207e3bba6c272d9f3c45af1b6d 100644 GIT binary patch delta 338 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 literal 0 HcmV?d00001 diff --git a/companion/src/images/library/00020.png b/companion/src/images/library/00020.png new file mode 100644 index 0000000000000000000000000000000000000000..9f3c5d78e040bf7ea81c74d87f2edabced38ae62 GIT binary patch literal 764 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 XwlJGfv{%5+{}n4Ud(#?Y-?)DPb8?TN literal 0 HcmV?d00001 diff --git a/companion/src/images/library/00024.png b/companion/src/images/library/00024.png new file mode 100644 index 0000000000000000000000000000000000000000..2b2081c886fb7876f9221ab4d9f8fcc9cf3ca492 GIT binary patch literal 3727 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 KMNUMnLSTYNUeP%K literal 0 HcmV?d00001 diff --git a/companion/src/images/library/10104.png b/companion/src/images/library/00051.png similarity index 100% rename from companion/src/images/library/10104.png rename to companion/src/images/library/00051.png diff --git a/companion/src/images/library/00100.png b/companion/src/images/library/00100.png new file mode 100644 index 0000000000000000000000000000000000000000..12fd5b70f79fceadc97360ddc52f0243e143b280 GIT binary patch literal 2294 zcmVb3q;Ln&up^;Ph#0N)DmtpMK&@T~w}*p$8dOIM?)>pe*_2spH zeMJQL;yNI?HOOCY0qD(FgupKh1QW6(nWZcBLGdLmKL=>dR|LUVEx?WBRx7!a;?L@L z#7}x_V={r(NuyV)ourpnf=MY!OP#wbF2A<5 zH_6!87_C)uKwEb3-XQB7Q79xQZw>zDovb#cuJ{~Wg{wgl2Iwyxs_G2q%y=OUXTWpHy%vU0i#N1FUgYmA_B{@)_WU+;u)PK z)CL<55=vWZrP_}+M#-#@Vg!I;`9&t&VU-VeGnO=b){5^^#r8Y%42GR{q!bvPP+wt@UX2!3XC%ol8`hGzv$B&Ni0S$NttHtV01@ z*S&p|8$9nw*61Uc7-chh*~*O{-NwIFMy0|!#-??QajK(`Iq>4BP&oxZoFQ}PJEz#~ zm91J~P)5mKu>fnwz}^C7yznebf!cfDhhnJhvYqG(gJShMV7`O$T{xd znb-f>{g+qMexGQE&l;|YmjAgF%#PY+nv*UTc94`Z`e2gtE@me)j!Id%h}%{rp)$ww zs(5PRg_i$;1$f%^$x#<(bd6bwVnOgBG~XNVC94lfR;otc{DAe!y0vASBdx0igFDWgCOa zXfW9XzbCzy&Fnr113Cu>tEI_DrM1zZiB>O6DwA5T)Ho^~{l!*iZ|l3DzF8S8-Vl&> zZt;8Xb@pz&(?r*l!5pt#fFfG($pY18S#K4fw{lPz)n>`se!*>4cG_TxA|z6l-1tBD zX0pAqX%_-do#SNk$|qox)qmWEFH+FD`M4a-9>rwY{t~OKKH% z{wJ{H?C8n`?HLw${T$Z^V8A5l+&Sp<+Gp6F{XYc(#gF1Hq9B=fPu|loH zjnaT4P8tKU6KbQRd9iNzAUk}Bc;orC!%F4RjXGk^a~uEQi1niS>Sv+XW3b3dQaO6- zC#?O`jY=}B%*sU*=1>Jg*soVIL+N)cND4#qq|om?JmZb(S;<;QZydt*-q?k5cw&W& z+Cgm$37r*Tsh)~)482hsuPBW!IvcD*yG>zdKh9TH0h(u+J=5wFI*{z#{GuGSV{}6q z_;U?!c+t_=pwgJ!|He_)9|dhWn)w`>G+K3o==n}g=BQ=Xf%h@sJ(M%(wb4*C>82R zB+tp^z1cB>y!28S@I;5h#mA=IA2w~Nc3jSynAMBv8dYu#{^j1vR%>t6EoV`KS{q5! z3l!k;-|L(W*7U)jJ-2rDXcG}?=be?Tc2XGq;HT)LS`N=Ly0gd1;d&TwouIml@cd(* zRz>8R^tN`f*V_nfj+#g%eil=WV1tF>rs14mcm3UHU5Xa<>6% zhlucpkk#iOddy3z@h2I9q|}?N9IwD8mZ()EN=4A(pq3qiIns4m;IaZd`MPOI4z8W~ zWHcTk#{DH|SFgQ%%aK_7LebZ}=!oAU>{lOwcKLzaf3EiX-`|tlFQx=9u|QLZmGKjQ z;P6>8!I$lTF^*6UuQP0QKP5=M^ literal 0 HcmV?d00001 diff --git a/companion/src/images/library/20004.png b/companion/src/images/library/00101.png similarity index 100% rename from companion/src/images/library/20004.png rename to companion/src/images/library/00101.png diff --git a/companion/src/images/library/20001.png b/companion/src/images/library/00102.png similarity index 100% rename from companion/src/images/library/20001.png rename to companion/src/images/library/00102.png diff --git a/companion/src/images/library/20002.png b/companion/src/images/library/00103.png similarity index 100% rename from companion/src/images/library/20002.png rename to companion/src/images/library/00103.png diff --git a/companion/src/images/library/20003.png b/companion/src/images/library/00104.png similarity index 100% rename from companion/src/images/library/20003.png rename to companion/src/images/library/00104.png diff --git a/companion/src/images/library/10030.png b/companion/src/images/library/00105.png similarity index 100% rename from companion/src/images/library/10030.png rename to companion/src/images/library/00105.png diff --git a/companion/src/images/library/10031.png b/companion/src/images/library/00106.png similarity index 100% rename from companion/src/images/library/10031.png rename to companion/src/images/library/00106.png diff --git a/companion/src/images/library/00201.png b/companion/src/images/library/00201.png new file mode 100644 index 0000000000000000000000000000000000000000..a5e6349a3f0c74a46f1690328ff64fcec0518064 GIT binary patch literal 1654 zcmV-+28sEJP)MtqrG5o(cC!|IYz1k$Ag( zdlXR)`@gj7xBT+#A&3=1caW)hip|~8`OF?LvP;K+h(+cpDc!Z%Kcn_}Ma*oVYA#eB zRGr7TyXe^f5Gg}|s#lF_V)k<5tB5~S2*@#IWtU@%WXSYbqhtR%n<vOz5_8vA$B^yvnMdtKk@4~oqObS<=U&7s|% zqvK)#5RE$;035!so)E`j*85pb-1GHS*i=ko{l1^i$pI=>*a-FRyPE~-VQ_$GUL3Z} zb-tcC?q!Oz(yRbus+f2SmHjylvpOoRB*zhrb84D39krhx+^Kq zOROjFsnbl9B%s0L&tHav9=p{U5?Z5mw^>9;C~Sx~DFMPPxDwO?71#k4v%XpIoiO{J<` z6-PHFYHo>_^T7BD9DQZw{>}F7me*Sh154Dj!VQ4{bCm39Y50T?5b9o3PR)zHg~L?_ zfWxorjn2>@y2i(|&{IOd7gp(jJ~?`JRJ==>?uMpa+QEdjg}|b`6CxNie><8h$)bYEuS;yw5*y7I3f8 z$>rr5*0oengNkbxhQ)_AUiSwPXb%_J_g3td&SifL0D7I+!~1P_$jJt6Jg(V;bv|5> z-v&V6It+dHE{P)@1A1EL)$5D0e_(GLp}@vh$mS(w-IIioR^^PVdmRTB7W&1lK0D0N z6S^Ils}#w*wt*|MW3Z3Z@r3|H3yZQ|9(^oFeKm?T~Gk+3nZjCSW~)1O@ag|sGER;SCbm-U%IINo1R9{!Qd*Y z-Ks1Pia=JBxO5nKoCS~E>(4^ z>eT6(kdlA&id-FVb->jDR|i}jaCN}d0apk7n5!1Fk9=SLh(?#@9Nk5F@_&Db6;PT$ zk$?a2DG;m$(MFIYqa;b6W&U@DfS}Q<4IrH;UA_ZwQz-S)S?a~JtXn%Nm#TMWZtN|B zXb~);LzLGq?-X2Fcp)%rzukx(0+yLj0vKhhq|ST3t?nbGzTU5fC24IX&U= z+K9zU!tj~2<)|V-2U81%j8}d_j8(8TP}2f)o`dlfqsSq%))7Bo6q}2&KRMtWzosN(s^W z8N0wU3_~q~!7A5}(X%{Ap9eYHBtBH3kJ)ms01P6srCH&z(| zNzw^A{F$NJ>ji_9Tjj^4kf0Wh+1x4Awvyi^lPK9gIAViYAxV#RnX@{eaxYogN%{}! zz>Nl@R)ZIqRDxiAyrrNLY(znA&=@6KlLBj^@rFnxo6pqh$R|2#7)!JPOH5 z$VD#YD5spu(Hk3$d!14zSWt=PoXy)zoEEiT1)Uv&-vrx_820;r%40&MCur7L5OAP3 z2U+XTo*KPIM~*qGoUxVhL4;zi6thB~N0~)q(&!|??4|oB8N?EnYluf&sN$?IcCM7${F|es54`qZaX)3PDn;jMi!t8Tug` zyJ#e{9*yz=h!0icYh;u32m;E}=l)uk;~KFht3M$}y!6&jwnF}v!g8G5Z97uk%1#=T1K4oxh}$ zG@_l2Sz*>1^)@Ea$`;S}!14)-;70GiR&KJoGaD@mi&10LTG?5=%3$AkZLKj$cJ39& z3gUZ3Ku}uDN^jlfT0qJ!=u`^9XcRSBu1cal&j`-EKX_(Qw2+J{!Op+jWxcQs#}d*`l>r1hb^g z15^EM7&ybez+Vj+t@G2GYhxaFJ8c#%XXS<2-&ys5>PUeP{*C$XgGfS9^l*USFBHI^gPns{{Vg Z>;Jp4bt4A>%Rm4C002ovPDHLkV1k!Q|9AiZ literal 0 HcmV?d00001 diff --git a/companion/src/images/library/10036.png b/companion/src/images/library/00402.png similarity index 100% rename from companion/src/images/library/10036.png rename to companion/src/images/library/00402.png diff --git a/companion/src/images/library/10038.png b/companion/src/images/library/00403.png similarity index 100% rename from companion/src/images/library/10038.png rename to companion/src/images/library/00403.png diff --git a/companion/src/images/library/10039.png b/companion/src/images/library/00404.png similarity index 100% rename from companion/src/images/library/10039.png rename to companion/src/images/library/00404.png diff --git a/companion/src/images/library/00501.png b/companion/src/images/library/00501.png index 51e85006a8615d554c0b7be062363b33b088ddc2..44bb7ad5a8361da7f343a8d0aecb47e151b015a2 100644 GIT binary patch delta 821 zcmV-51IqlW1>Xjc7(WOA0002@y&$6i0007FOGiWi|A&vvzW@LL32;bRa{vGf6951U z69E94oEQKA00(qQO+^RZ0vHMdF?{JQz>^ySBYy(VNklZsc767Xn0lz?G3nS?a!UZV+1on`EK$u^F#~Isk0P?sFAA^({#`jGji!}?XtP0%#$$A+= zjP$!?n~DQu1jn|01MI=isd;}=Gu+Qz?*Y_XLnUT%;VNPPHF@jhxz^qa0=#M>^2Ht= z#&o&`;CN^F&~40QAdwn86@-^V$HEDVdVi{11Gq)}LIEf~m3oxz=)i1K)7n-GutNc( zN|HHb%hN(p1tV1{+RwSn?hp|-(lLOn%)>*G!(ePshf8OAZop!i*e!G!ER1CbJFU)= z2cHnYHOr68eAwww-DG!(FAK+=Ll6@q^bbL>7i1Jb+Zfoiq--((W{f-ljg^-T27fTA z?13}{0HEp$r`)6?d9Ey3t{tfnYN5#$Pk^9mosXPxG9n%^P+orlg0gKurmK)lmd1{7C0vhyM$^45>*vBrXxqDc%24! z5{;%Mo9iou$8gU|RiwB!*~0mZ#eZIQF`Tb1K`Qs14Hd&X`_D@bD6`qegNR|$6R7qn zp7e9!OXh@7@~J*RQ)?;aPWw!-ZJXcf3ddmsn<0=zLpH?)(7MFPZxn`8pK%ZzyFhjD zC&%^PgTMzV-*-XYmdic(XKJhf_$a>j5j;8Ya=f*P@U#cw7JX4ZeANR>t!jXKVd8@O zw1-`Q`nz+>!xZ>)eJ3YRQ?RnozT$k`1HVVUX!1(?Cjft^PEDKe6#%~@^<>7j(Dj8F zm@7ESKAMlG;hYX=-T=|Q=z(FdX7M{Snwk9oAJQ^lZ{=M400000NkvXXu0mjfs}Xbi delta 638 zcmcc5wu*IvL_H$|5d2!}bO}gt7I;J!Gca%incNJFPt4cuXJBC5>FMGaVsSe5vUT1a z0|B-Ni4qPkZ{#ILgnMKjV62!bb1=1w;nJbj^+#RxobD%hiJ7Q>=GV*&*AiRpFY^4L z;K}JWF)B856?O}&M9C#CtzeobfAD%i)3fi^wJv8*me%h+FXv$R_Vh`GCxY9B&N7@= z&NEvf9`1JM$)_a-m+uRf&+TGg@;q){-hGCN&GOY<77kx+1!MI&72aKIX3=3X&vL zWaypvW!c+&Sqb;e^=f}Z9pnRBEozgQeHq_&m2dEHbT&WnYr;wX9~T(7X0Gv_%s6ZI ziMJO#nAiN4`_CY(kQcz%@}0+yaot?Ty&UBZv&0`UNqjhF&lka?$979W^WuZlcB^cb zXZGwYXBGK1xO_L4%zql*zJj&F^PgD*a!9z~x$xiJyY6}vt zZTDaNBD-g=*@|m!mJA0A_pmRi6JTHPzKFkS#zVm)r#avJ;&=1iF7W?keLXNnMM_*F zN*qf|GV+TU98-!i6Y~@tbCcLpi_+`z!=omKE9Wq%f|R5rmZVxG7o`Fz1|tJQBV7YS zT|?6lLo+Kw6Dt!lZ39Cq1A{AbWxoN|gM2TZ*Nk)DVgJVijW@4U#V{TGvQF>i|coa}x6eRDQpPQSSSAwdbKhxs? zP=P8)K}upts#S7PDv)9@GB7mKH89jQGz~E{vobWXGBMLOFtjo-xH4Dv8;XY9{FKbJ XO57Tj9$4xH)WG2B>gTe~DWM4fs_bf# diff --git a/companion/src/images/library/10098.png b/companion/src/images/library/10098.png deleted file mode 100644 index 44bb7ad5a8361da7f343a8d0aecb47e151b015a2..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 863 zcmV-l1EBngP)*cxD-UmK)lmd1{7C0vhyM$^45>*vBrXxqDc%24!5{;%Mo9iou z$8gU|RiwB!*~0mZ#a?zXoUblHD)*fY6~jCG&r1#{v)RXkh+)zbsP-wI^mE}$=7do4 zsXjncYboYV`%JKHo8RgR$6*7TA&^BwHpKJn4002ovPDHLkV1k75e2)MC diff --git a/companion/src/images/library/10085.png b/companion/src/images/library/10101.png similarity index 100% rename from companion/src/images/library/10085.png rename to companion/src/images/library/10101.png diff --git a/companion/src/images/library/10088.png b/companion/src/images/library/10102.png similarity index 100% rename from companion/src/images/library/10088.png rename to companion/src/images/library/10102.png diff --git a/companion/src/images/library/10090.png b/companion/src/images/library/10103.png similarity index 100% rename from companion/src/images/library/10090.png rename to companion/src/images/library/10103.png diff --git a/companion/src/images/library/10501.png b/companion/src/images/library/10501.png new file mode 100644 index 0000000000000000000000000000000000000000..51e85006a8615d554c0b7be062363b33b088ddc2 GIT binary patch literal 682 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 LNkvXXu0mjfm0HGb diff --git a/companion/src/images/library/30005.png b/companion/src/images/library/30005.png deleted file mode 100644 index 8761d4fcb984cb975b78e7d3febab2bff3719b8b..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 2395 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 N002ovPDHLkV1jr;h?4*S From ca4c7b4dc13cef7d8c64e273df2cfa368ddb6e56 Mon Sep 17 00:00:00 2001 From: Kjell Kernen Date: Mon, 24 Feb 2014 16:36:45 +0100 Subject: [PATCH 62/89] Corrected index error in general edit --- companion/src/generaledit.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/companion/src/generaledit.cpp b/companion/src/generaledit.cpp index 6c5b6dfc9..8cccc654c 100644 --- a/companion/src/generaledit.cpp +++ b/companion/src/generaledit.cpp @@ -74,7 +74,7 @@ GeneralEdit::GeneralEdit(RadioData &radioData, QWidget *parent) : if (!name.isEmpty()) { ui->profile_CB->addItem(name, i); if (i==g.id()) { - ui->profile_CB->setCurrentIndex(ui->profile_CB->count()); + ui->profile_CB->setCurrentIndex(ui->profile_CB->count()-1); } } } From 0f3e6581bd86ac4e5edfa0900a14c4878b3ecc4c Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Mon, 24 Feb 2014 18:20:29 +0100 Subject: [PATCH 63/89] Update DONATIONS.txt --- DONATIONS.txt | 2 ++ 1 file changed, 2 insertions(+) diff --git a/DONATIONS.txt b/DONATIONS.txt index f3bf27e41..45b1c981b 100644 --- a/DONATIONS.txt +++ b/DONATIONS.txt @@ -325,3 +325,5 @@ Reginald H Millsom Emanuel Stassar Pierluigi Sommaruga Rafael Eric Suarez Nordlow +A Harris + From 0029f57413d77fd1dc5891141cb9605ff94d5fa9 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Mon, 24 Feb 2014 19:52:35 +0100 Subject: [PATCH 64/89] Conversions from older EEPROM for duration/delay fields (x5) --- companion/src/firmwares/opentx/opentxeeprom.cpp | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/companion/src/firmwares/opentx/opentxeeprom.cpp b/companion/src/firmwares/opentx/opentxeeprom.cpp index 37f148900..dff4d73fb 100644 --- a/companion/src/firmwares/opentx/opentxeeprom.cpp +++ b/companion/src/firmwares/opentx/opentxeeprom.cpp @@ -1196,8 +1196,9 @@ class LogicalSwitchField: public TransformedField { if (IS_ARM(board)) { internalField.Append(new ConversionField< UnsignedField<8> >(csw.func, &functionsConversionTable, "Function")); - internalField.Append(new UnsignedField<8>(csw.delay)); - internalField.Append(new UnsignedField<8>(csw.duration)); + int scale = (version >= 216 ? 0 : 5); + internalField.Append(new ConversionField< UnsignedField<8> >(csw.delay, 0, scale)); + internalField.Append(new ConversionField< UnsignedField<8> >(csw.duration, 0, scale)); if (version >= 214) { internalField.Append(new ConversionField< SignedField<8> >((int &)csw.andsw, andswitchesConversionTable, "AND switch")); } From 9992c1f79ce63550bb1e7d8188df3d3b2d3bf4d3 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Mon, 24 Feb 2014 20:58:59 +0100 Subject: [PATCH 65/89] Update DONATIONS.txt --- DONATIONS.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/DONATIONS.txt b/DONATIONS.txt index 45b1c981b..c85c6de97 100644 --- a/DONATIONS.txt +++ b/DONATIONS.txt @@ -326,4 +326,4 @@ Emanuel Stassar Pierluigi Sommaruga Rafael Eric Suarez Nordlow A Harris - +Stefan Grunenberg From 06115fdaed78193aba05f0a37f0df19c16dcf6bb Mon Sep 17 00:00:00 2001 From: Jacek Drewniak Date: Mon, 24 Feb 2014 21:44:11 +0100 Subject: [PATCH 66/89] PL translation fixes --- companion/src/translations/companion_pl.ts | 457 ++++++++++++--------- 1 file changed, 254 insertions(+), 203 deletions(-) diff --git a/companion/src/translations/companion_pl.ts b/companion/src/translations/companion_pl.ts index bd3013a8a..ab649090f 100644 --- a/companion/src/translations/companion_pl.ts +++ b/companion/src/translations/companion_pl.ts @@ -57,22 +57,22 @@ CurveGroup - + Diff Róźnicowość - + Expo Expo - + Func Funkcja - + Curve Krzywa @@ -4105,70 +4105,70 @@ p, li { white-space: pre-wrap; } QObject - + Rud SK - + Ele SW - + Thr Gaz - + Ail Lotki - - + + P1 Potencjometr 1 - - + + P2 Potencjometr 2 - - + + P3 Potencjometr 3 - + S1 Potencjometr 1 - + S2 Potencjometr 2 - + LS Lewy suwak - + RS Prawy suwak @@ -4687,26 +4687,26 @@ p, li { white-space: pre-wrap; } - + ---- - + THR THR - + ON Włącz - + OFF Wyłącz @@ -5153,7 +5153,7 @@ p, li { white-space: pre-wrap; } - + Warning Ostrzeżenie @@ -5163,94 +5163,94 @@ p, li { white-space: pre-wrap; } EEPROM zapisany z tymi ostrzeżeniami: - - + + FM%1 FP%1 FM%1 - + Input%1 Wejście %1 - + English Angielski - + French Francuski - + Italian Włoski - + German Niemiecki - + Czech Czeski - + Slovak Słowacki - + Spanish Hiszpański - + Portuguese Portugalski - + Polish Polski - + Finnish Fiński - + No Nie - + RotEnc A Pokrętło :A - + Rot Enc B Pokrętło :B - + Rot Enc C Pokrętło :C - + Rot Enc D Pokrętło :D - + Rot Enc E Pokrętło :E @@ -5572,133 +5572,133 @@ p, li { white-space: pre-wrap; } Pokrętło - + !Flight mode %1 !Faza lotu %1 - + Flight mode %1 Faza lotu %1 - + Yellow Żółty - + Orange Pomarańczowy - + Red Czerwony - + Winged Shadow How High - + Winged Shadow How High (not supported) Winged Shadow How High (nie obsługiwane) - + FrSky Sensor Hub Hub sensora FrSky - - + + None Żaden - + Imperial Imperialne - + Metric Metryczne - + Extra Fine Bardzo dokładne - + Fine Dokładne - + Medium Średni - + Coarse Gruby - + Exponential Eksponencjalny - + Count Up Licz - + Count Down Odliczaj - + %1:%2, - + : %1 Channels, %2usec Delay :Kanały %1, opóźnienie %2usX - + Flight modes(%1) Fazy lotu(%1) - + Flight mode(%1) Faza lotu (%1) - + Rudder SK - + Elevator SW - + Throttle Gaz - + Aileron Lotki @@ -5709,43 +5709,43 @@ p, li { white-space: pre-wrap; } - - + + --- - + Rud Trim Trymer SK - + Ele Trim Trymer SW - + Thr Trim Trymer gazu - + Ail Trim Trymer lotek - + Rot Enc Pokrętło - + Swedish Szwedzki - + CH%1 Kan %1 @@ -5848,46 +5848,46 @@ p, li { white-space: pre-wrap; } Zwiększanie - + Own value Własny Wartość - + Flight mode %1 value Flight phase %1 value Wartość Fazy lotu FL%1 - + Keys Przyciski - + Sticks Drążki - + Keys + Sticks Przyciski i Drążki - + -GV%1 -ZG%1 - + GV%1 ZG%1 - + Simulator for this firmware is not yet available Nie jest dostępny symulator dla tego firmware @@ -5965,17 +5965,17 @@ Zespół OpenTX/Companion. Użyj trymerów dla Fazy Lotu %1 + Własne trymery jako offset - + FW: %1 FW:%1 - + Pict: %1 Obrazek:%1 - + Profile image Obrazek Profilu @@ -7135,11 +7135,21 @@ To ustawienie jest używane przez szablony, określa jakie wyjście przypisane j SD Structure path Struktura karty SD + + + Firmware Variant + Wariant Firmware + Select Image Wybierz obrazek + + + Firmware File + Plik Firmware + Offer to write FW to Tx after download @@ -7166,9 +7176,8 @@ To ustawienie jest używane przez szablony, określa jakie wyjście przypisane j Wyczyść obrazek - Firmware - Firmware + Firmware @@ -7246,53 +7255,53 @@ To ustawienie jest używane przez szablony, określa jakie wyjście przypisane j Uaktywnij automatyczny backup przed zapisem firmware - + Select your snapshot folder Katalog zrzutów - - + + No joysticks found Brak oysticka - + Select your library folder Wybierz katalog bibliteki - + Select your Models and Settings backup folder Wybierz folder do backupowania Modeli i Ustawień - + Select Google Earth executable Wybierz wykonywalny plik Google Earth - + Select the folder replicating your SD structure Wybierz folder do zreplikowania struktury Twojej karty SD - + Not possible to remove profile Usunięcie profilu jest niemożliwe - + The default profile can not be removed. Podstawowy profil nie moze być usunięty. - + Open Image to load Otwórz obrazek do załadowania - + Images (%1) Obrazki (%1) @@ -7676,250 +7685,292 @@ m2560 dla platformy V4 Własne logo - - + Write to TX Zapisz do radia - + <html><head/><body><p>Modify calibration parameters using settings from current profile</p></body></html> <html><head/><body><p>Zmiana parametrów kalibracji przy użyciu aktualnego profilu</p></body></html> - + Patch calibration setting from profile Zamień ustawienia kalibracji wartościami z profilu - + <html><head/><body><p>Modify HW parameters using settings from current profile</p></body></html> <html><head/><body><p>Zmień ustawiania parametrów HW przy pomocy wartości z aktualnego profilu</p></body></html> - + Patch HW setting from profile Zmień ustawiania parametrów HW wartościami z profilu - + Date & Time Data i Czas - + + Use firmware start screen + Użyj ekranu startowego z firmware + + + + Use another start screen + Użyj innego ekranu startowego + + + + Use profile start screen + Użyj ekranu startowego z profilu + + + + Use library start screen + Użyj ekranu startowego z biblioteki + + + SVN - + Variant Wariant - Invert Color - Odwróć kolory + Odwróć kolory - Load Image - Otwórz logo + Otwórz logo - Open Splash Library - Otwórz bibliotekę obrazków + Otwórz bibliotekę obrazków - - ... - - - - Substitute image in firmware - Zmień logo w firmware + Zmień logo w firmware - - + + Browse for file Przeglądaj pliki - + Allows Companion to write to older version of the firmware Pozwól Companion na zapis do starszej wersji firmware - + Backup and restore Models and Settings Zbakupuj i odtwórz Modele i Ustawienia - Use image in settings - Użyj Logo w ustawieniach + Użyj Logo w ustawieniach - + Check Firmware compatibility Sprawdź kompatybilność firmware - + Current Profile Aktualny profil - + Cancel Przerwij - + Write firmware to TX Zapisz firmware do radia - + Current profile Aktualny profil - - - - - - + + + + + + Warning Ostrzeżenie - %1 is not a known firmware - %1 nie jest znanym firmware + %1 nie jest znanym firmware - Burn anyway ! - Wypiecz mimo wszystko ! + Wypiecz mimo wszystko ! - - - - - + + + + + + + - - - - + + + + + Error Błąd - + Unable to find file %1! Nie mogę odnaleźć pliku %1! - - - + + + Error opening file %1: %2. Błąd otwarcia pliku %1: %2. - + Write Models and Settings to TX Zapisz Modele i Ustawienia do radia - + Write Models and Settings in %1 to TX Zapisz Modele i Ustawienia w %1 do radia - + Open Firmware File Otwórz plik Firmware - + Choose file to load Models and Settings from Wybierz plik Modeli i Ustawien do wczytania - - - + + %1 may not be a valid firmware file + %1 moze nie być prawidłowym plikiem firmware + + + + + Invalid binary Models and Settings File %1, Proceed anyway ? Nieprawidłowy plik Modeli i Ustawień : %1. Kontynuować ? - + Error reading file %1: %2. Błąd odczytu pliku %1: %2. - - Open Image to load - Otwórz plik z logo + + The firmware file is not valid. + Plik firmware jest błedny. - + + There is no start screen image in the firmware file. + Brak obrazka ekranu startowego w firmware. + + + + The profile image %1 does not contain an image. + Obraz profilu %1 nie zawiera obrazka. + + + + Open image file to use as Tx start screen + Otwórz plik obrazka by użyć go jako ekran startowy radia + + + + Image could not be loaded from %1 + Obrazek nie moze być załadowany z %1 + + + + The library image could not be loaded + Obrazek z biblioteki nie może być załadowany + + + Open Image to load + Otwórz plik z logo + + + Images (%1) Obrazki (%1) - - Cannot load %1. - Nie mogę załadować %1. + Nie mogę załadować %1. - + Cannot save customized firmware Nie mogę zapisać przystosowanego firmware - + Custom image not found Własny obrazek nie odnaleziony - + No firmware selected Brak wyboru firmware - + Wrong radio calibration data in profile, Settings not patched Błędna kalibracja radia w profilu, Ustawienia nie spatchowane - + Wrong radio setting data in profile, Settings not patched Błędne ustawienia radia w profilu, Ustawienia nie spatchowane - - + + Cannot write file %1: %2. Nie mogę zapisać pliku %1: %2. - + Error writing file %1: %2. Błąd zapisu pliku %1: @@ -8537,75 +8588,75 @@ m2560 dla platformy V4 - - + + + - Error Błąd - + Cannot load the image file %1. Nie mogę załadować pliku obrazka %1. - + Cannot load the profile image %1. Nie mogę załadować obrazu Profilu %1. - + Cannot load the library image %1. Nie mogę załadować obrazu biblioteki %1. - + File Saved Plik Zapisany - + The image was saved to the file %1 Obraz został zapisany do pliku %1 - + Image Refresh Error Błąd odświeżenia obrazka - + Failed to refresh image from file %1 Nieudane odswieżenie obrazka z pliku %1 - + File Save Error Błąd zapisu pliku - + Failed to write image to %1 Nieudany zapis obrazka do %1 - + Open Image to load Otwórz obrazek do załadowania - + Open Firmware File Otwórz plik Firmware - + Can not load embedded image from firmware file %1. Nie mogę załądować wbudowanego obrazka z pliku Firmware %1. - + Images (%1) Obrazki (%1) @@ -10614,32 +10665,32 @@ Mode 4: splashLibrary - + ... - + Splash Library - page %1 of %2 Biblioteka obrazków - strona %1 z %2 - + Warning Ostrzeżenie - + Invalid image in library %1 Nieprawidłowy obrazek w bibliotece %1 - + Information Informacja - + No valid image found in library, check your settings Nie znaleziono prawodłowego obrazka w biblitece, sprawdź ustawienia From 2e14e5d9c84439ff84a48f6d508cfc47e44fb814 Mon Sep 17 00:00:00 2001 From: Kjell Kernen Date: Mon, 24 Feb 2014 22:50:03 +0100 Subject: [PATCH 67/89] Swedish Companion translation --- companion/src/translations/companion_sv.ts | 2031 ++++++++++++-------- 1 file changed, 1176 insertions(+), 855 deletions(-) diff --git a/companion/src/translations/companion_sv.ts b/companion/src/translations/companion_sv.ts index 9b2636f07..091cd0560 100644 --- a/companion/src/translations/companion_sv.ts +++ b/companion/src/translations/companion_sv.ts @@ -57,7 +57,7 @@ CurveGroup - + Diff Diff @@ -143,7 +143,7 @@ CustomFunctionsPanel - + Switch Brytare @@ -163,17 +163,17 @@ Effekt - + CF%1 - + - + ON På - + Error Fel @@ -183,7 +183,7 @@ Kan inte hitta ljudfilen %1! - + &Delete &Ta bort @@ -601,7 +601,7 @@ Om fältet lämnas tomt så är filtret aktivt hela tiden. Allmänna inställningar - + General settings used throught the transmitter. These will be relevant for all models in the same EEPROM. Allmänna inställningar för sändaren @@ -1541,7 +1541,7 @@ Mode 4: Spänning - + Warning Varning @@ -1557,12 +1557,12 @@ Mode 4: Felaktig information i profilen, hårdvaruinställningar lästes inte in - + Do you want to store calibration in %1 profile<br>overwriting existing calibration? Vill du skriva över existerande kalibreringsdata<br>i profilen %1 med de nuvarande? - + Calibration and HW parameters saved. Kalibrering ojch hårdvaruinställningar sparades. @@ -1677,7 +1677,7 @@ Mode 4: PPMSim - + If you enable FAI, you loose the vario, the play functions, the telemetry screen. This function cannot be disabled by the radio. Are you sure ? @@ -1844,25 +1844,25 @@ FAI-funktionen kan inte slås av i sändaren. InputsPanel - + Move Up Flytta uppåt - - + + Ctrl+Up Ctrl+Up - - + + Move Down Flytta nedåt - - + + Ctrl+Down Ctrl+Down @@ -1887,12 +1887,12 @@ FAI-funktionen kan inte slås av i sändaren. Brytare(%1) - + Clear All Settings Radera alla inställningar - + Not enough available inputs! För få filter är tillgängliga! @@ -2064,39 +2064,39 @@ FAI-funktionen kan inte slås av i sändaren. MainWindow - - - - + + + + File loaded Filen har laddats - + - - + + Save As Spara Som - - + + No updates available at this time. Inga updateringar finns tillgängliga. - - - - + + + + Unable to check for updates. Det gick inte att söka efter uppdateringar. - + Executable (*.exe) Program (*.exe) @@ -2106,110 +2106,96 @@ FAI-funktionen kan inte slås av i sändaren. Vill du starta installationsprogrammet? - + Do you want to write the firmware to the transmitter now ? Vill du skriva firmware till sändaren nu? - + A new version of %1 firmware is available (current %2 - newer %3). Do you want to download it now ? En ny version finns tillgänglig av %1 fimware (Din version %2 - Ny version %3). Vill du ladda ned den nya versionen nu ? - Open - Öppna + Öppna - + File saved Filen sparades - + Copyright Copyright - New - Ny + Ny - Open... - Öppna... + Öppna... - Save... - Spara... + Spara... - Save As... - Spara Som... + Spara Som... - + Exit Avsluta - Cut - Klipp Ut + Klipp Ut - Cut current selection to the clipboard - Klipp ut markeringens innehåll till klippbordet + Klipp ut markeringens innehåll till klippbordet - Copy... - Kopiera... + Kopiera... - Copy current selection to the clipboard - Kopiera markeringens innehåll till klippbordet + Kopiera markeringens innehåll till klippbordet - Paste... - Klistra In... + Klistra In... - Paste clipboard into current selection - Klistra in klippbokens innehåll i det valda avsnittet + Klistra in klippbokens innehåll i det valda avsnittet - + Classical Klassiskt - The classical Companion icon theme - Det klassiska Companion-temat + Det klassiska Companion-temat - The new Companion 2 icon theme - Det nya Companion2-temat + Det nya Companion2-temat - Companion2 - Companion2 + Companion2 - + Monochrome Monokromt @@ -2234,137 +2220,119 @@ Vill du ladda ned den nya versionen nu ? Använd systemspråket i menyerna - About - Om + Om - Print - Skriv ut + Skriv ut - + Print current model Skriv ut modell - Simulate - Simulera + Simulera - Simulate selected model - Simulera modell + Simulera modell loadBackup... Ladda backup från fil... - Logs - Loggar + Loggar - Setting... - Inställningar... + Inställningar... - Downloads... - Nedladdningar... + Nedladdningar... - Check for updates... - Sök efter uppdateringar... + Sök efter uppdateringar... - + Edit Tx Splash Image... Startbildsredigerare... - edit the splash screen of your TX - Editera startbilder för din sändare + Editera startbilder för din sändare - List programmers - Programmerare + Programmerare - + Fuses... Säkringar... - Configure connection software... - Inställningar för kommunikation... + Inställningar för kommunikation... - + Save Tx Models and Settings to file Spara sändarens Modeller och Inställningar till fil - Contributors - Bidragande + Bidragande - + A tribute to those who have contributed to OpenTX and Companion Ett tack till alla de som bidragit till OpenTX och Companion - + Settings Inställningar - + Read/Write Läs/Skriv - - &%1 %2 - &%1 %2 + &%1 %2 &New &Ny - Create a new file - Skapa ny fil + Skapa ny fil &Open... &Öppna... - Open an existing file - Öppna en existerande fil + Öppna en existerande fil &Save &Spara - - Save the document to disk - Spara dokumentet till fil + Spara dokumentet till fil Save &As... @@ -2379,12 +2347,12 @@ Vill du ladda ned den nya versionen nu ? &Sök efter uppdateringar... - + Display previous message again at startup ? Skall föregående varning visas igen vid uppstart ? - + Firmware does not longer fit in the Tx, due to selected firmware options Firmware får inte rum i minnet på grund av att för många funktioner aktiverats @@ -2394,12 +2362,12 @@ Vill du ladda ned den nya versionen nu ? Tillfälligt fel i byggservern. Försök igen senare - + Firmware does not fit in the Tx, due to selected firmware options Firmware får inte rum i minnet på grund av att för många funktioner aktiverats - + Firmware %1 does not seem to have ever been downloaded. Version %2 is available. Do you want to download it now ? @@ -2408,12 +2376,12 @@ Version %2 finns tillgänglig. Vill du ladda ned den nu ? - + Write Models and settings from %1 to the Tx? Skriv Modeller och Inställningar från %1 till sändaren? - + Conversion failed Konverteringen misslyckades @@ -2428,7 +2396,7 @@ Vill du ladda ned den nu ? Säkerhetskopieringen misslyckades - + OpenTX Companion - FW: %1 - Profile: %2 OpenTX Companion - FW: %1 - Profil: %2 @@ -2437,7 +2405,7 @@ Vill du ladda ned den nu ? &Inställningar... - + Edit Settings Redigera Inställningar @@ -2459,7 +2427,7 @@ Vill du ladda ned den nu ? &Avsluta - + Exit the application Avsluta programmet @@ -2496,16 +2464,15 @@ Vill du ladda ned den nu ? Ctrl+Alt+R - Configure software for reading from and writing to the transmitter - Inställningar för mjukvaran som kommunicerar med sändaren + Inställningar för mjukvaran som kommunicerar med sändaren &List programmers &Programmerare - + List available programmers Lista upp tillgängliga prorammerare @@ -2552,10 +2519,8 @@ Vill du ladda ned den nu ? Visa information om programmet - - Recent Files - Senaste Filer + Senaste Filer &File @@ -2570,22 +2535,22 @@ Vill du ladda ned den nu ? Companion - Editor för Modeller och Inställningar - %1 - + Checking for updates Letar efter uppdateringar - + A new release of Companion is available please check the OpenTX website! En ny version av Companion finns tillgänglig. Var god kontrollera OpenTX webbsida! - + Ignore this version (r%1)? Ladda inte ned versionen (r%1)? - + OpenTX Home Page: <a href='%1'>%1</a> OpenTX Hemsida: <a href='%1'>%1</a> @@ -2621,16 +2586,15 @@ Vill du ladda ned den nu ? Redigera programmets inställningar - Show Companion changelog - Visa en lista med förändringar av Companion + Visa en lista med förändringar av Companion &Write Models and Settings To Tx &Skriv Modeller och Inställningar till sändaren - + Write Models and Settings to transmitter Skriv Modeller och Inställningar till sändaren @@ -2648,8 +2612,84 @@ Vill du ladda ned den nu ? Write Firmware Skriv Firmware + + + New Models+Settings + Ny Modeller+Inställningar + + Create a new Models and Settings file + Skapa en ny Modeller och Inställningar-fil + + + + Open Models+Settings... + Öppna MOdeller+Inställningar... + + + + Save Models+Settings... + Spara Modeller+Inställningar... + + + + + Save Models and Settings file + Spara Modeller och Inställningar-fil + + + + Save Models+Settings as... + Spara Modeller+Inställningar som... + + + + Cut Model + Klipp ut Modell + + + + Cut current model to the clipboard + Klipp ut vald modell till klippbordet + + + + Copy Model... + Kopera Modell... + + + + Copy current model to the clipboard + Kopiera vald modell till klippbordet + + + + Paste Model... + Klistra in Modell... + + + + Paste model from clipboard + Klistra in modell från klippbordet + + + + The classic companion9x icon theme + Det klassiska companion9x-temat + + + + Yerico + Yerico + + + + Yellow round honey sweet icon theme + Yellow round honey sweet icon theme + + + Write firmware to transmitter Skriv firmware till sändaren @@ -2697,24 +2737,40 @@ Vill du ladda ned den nu ? - + File Arkiv - + Edit Redigera - - + + Help Hjälp - + + + Radio Settings Profile + Radioprofil + + + + Show recent Models+Settings documents + Visa senaste Modeller+Inställningar-dokument + + + + Show a selection list of radio settings profiles + Visa en lista med radioprofiler + + + Ready Redo @@ -2723,17 +2779,17 @@ Vill du ladda ned den nu ? &Bidragsgivare... - + Display previous warning again at startup ? SKall föregående varning visas igen vid uppstart ? - + - + - - + + @@ -2745,21 +2801,21 @@ Vill du ladda ned den nu ? Fel - + Cannot write file %1: %2. Filen %1 kunde inte skrivas: %2. - + New release available En ny version finns tillgänglig - - - + + + Error opening file %1: @@ -2768,68 +2824,72 @@ Vill du ladda ned den nu ? %2. - + Compilation server termporary failure, try later Tillfälligt fel i byggservern. Försök igen senare - - + + Compilation server too busy, try later Byggservern är upptagen. Försök igen senare - - + + Unknown server failure, try later Okänt server-fel. Försök igen senare - Compare... - Jämför... + Jämför... - + Compare models Jämför modeller - - + + Backup is impossible Säkerhetskopiering kan inte utföras - - + + The backup dir set in preferences does not exist Foldern för säkerhetskopior existerar inte - + Warning Varning - Firmware Profiles - Profiler för Firmware + Profiler för Firmware &Read/Write &Läs/Skriv - + Write Skriv - + + %2 + %2 + + + + Unable to find file %1! Kan inte hitta filen %1 ! @@ -2845,7 +2905,7 @@ Vill du ladda ned den nu ? ladda&Backup... - + Load backup from file Ladda backup från fil @@ -2858,46 +2918,45 @@ Vill du ladda ned den nu ? Ctrl+G - Open log file - Öppna loggfil + Öppna loggfil - - + + - + Taranis radio not found Hittade inte någon Taranis-sändare - - + + Impossible to identify the radio on your system, please verify the eeprom disk is connected. Det går inte att identifiera sändaren. Verifiera att EEPOROM-skivan är ansluteten. - + Yes Ja - + A new version of Companion is available (version %1)<br>Would you like to download it? An ny version av Companion finns tillgänglig (version %1)<br>Vill du ladda ned den? - - + + Compilation server requires registration, please check OpenTX web site Byggservern kräver registrering. Var god kontrollera OpenTX webbsida - + No Nej @@ -2915,34 +2974,40 @@ Vill du ladda ned den nu ? Vill du ladda ned firmware %1 nu ? - + Release notes contain very important informations. Do you want to see them now ? Release notes innehåller väldigt viktig information. Vill du läsa dem nu? - + The selected language will be used the next time you start Companion. Språket som valts kommer att användas nästa gång Companion startas. - - + + OK OK - + The new theme will be loaded the next time you start Companion. De nya ikonerna kommer att användas nästa gång Companion startas. - + The icon size will be used the next time you start Companion. Ikonernas storlek kommer att justeras nästa gång Companion startas. - + + + Open Models and Settings file + Öppna Modeller och Inställningar-fil + + + Firmware updates Firmware-uppdatering @@ -2954,14 +3019,14 @@ Vill du ladda ned den nu ? - + Read Models and Settings From Tx Läs Modeller och Inställningar från sändaren - + The file %1 has not been recognized as a valid Models and Settings file Write anyway ? @@ -2974,13 +3039,13 @@ Starta skrivningen i alla fall ? - + Backup Models and Settings From Tx Säkerhetskopiera Modeller och Inställningar från sändaren - + Cannot check Models and Settings compatibility! Continue anyway? Det går inte att verifiera att Modeller och Inställningar är kompatibla. Fortsätt i alla fall? @@ -2996,12 +3061,12 @@ Starta skrivningen i alla fall ? - + Write Models and Settings To Tx Skriv Modeller och Inställningar till sändaren - + Write Firmware To Tx Skriv firmware till sändaren @@ -3037,7 +3102,7 @@ Starta skrivningen i alla fall ? Det gick inte att säkerhetskopiera sändarens Modeller och Inställningar. Skrikvningen av firmware avbröts - + Save transmitter Models and Settings to File Spara sändarens Modeller och Inställningar till en fil @@ -3047,12 +3112,12 @@ Starta skrivningen i alla fall ? Det går inte att identifiera sändaren. - + Read Tx Firmware to File Läs Sändarens Firmware till Fil - + About Companion Om Companion @@ -3065,28 +3130,24 @@ Starta skrivningen i alla fall ? Ladda ned firmware och röstfiler. Definera profildata. - Check for new version of Companion - Sök efter ny version av Companion + Sök efter ny version av Companion Show Companion contributors list Visa vilka som bidragit till Companion - ChangeLog... - Förändringar... + Förändringar... - Firmware ChangeLog... - Firmware-förändringar... + Firmware-förändringar... - Show firmware changelog - Visa firmware-förändringar + Visa firmware-förändringar Configure transmitter start screen... @@ -3097,12 +3158,11 @@ Starta skrivningen i alla fall ? Inställningar för &kommunikation... - New Profile - Ny Profil + Ny Profil - + Create a new Radio Setting Profile Lägg till en ny profil med radio-inställningar @@ -3115,7 +3175,7 @@ Starta skrivningen i alla fall ? Det flerfärgade klassiska Companion-temat - + A monochrome black icon theme Ett monokromt svart tema @@ -3207,6 +3267,16 @@ Starta skrivningen i alla fall ? Use English in menus Använd Engelska i menyerna + + + Finnish + Finska + + + + Use Finnish in menus + Använd Finska i menyerna + French @@ -3278,12 +3348,102 @@ Starta skrivningen i alla fall ? Använd Ryska i menyerna - + + About... + Om... + + + + Print... + Skriv Ut... + + + + Simulate... + Simulera... + + + + Simulate current model + Simulera vald modell + + + Load Backup... Ladda backup från fil... - + + View Log File... + Visa loggfil... + + + + Open and view log file + Öppna och visa loggfil + + + + Settings... + Inställningar... + + + + Download... + Nedladdning... + + + + Check for Updates... + Sök efter uppdateringar... + + + + Check OpenTX and Companion updates + Sök efter uppdateringar av Companion och OpenTX + + + + Companion Changes... + Förändringar i Companion... + + + + Show Companion change log + Visa en lista med förändringar av Companion + + + + Firmware Changes... + OpenTX-förändringar... + + + + Show firmware change log + Visa en lista med förändringar av OpenTX + + + + Compare Models... + Jämför modeller... + + + + Edit the splash image of your TX + Editera startbilden' för din sändare + + + + List programmers... + Visa programmerare... + + + + Add Radio Profile + Lägg till Radioprofil + + + Manuals and other Documents Manualer och andra Dokument @@ -3293,7 +3453,28 @@ Starta skrivningen i alla fall ? Öppna OpenTX dokumentsida i en webbläsare - + + Configure Communications... + Kommunikations-inställningar... + + + + Configure software for communicating with the transmitter + Ställ in mjukvara för kommunikation med sändaren + + + + Contributors... + Bidragande... + + + + + Recent Models+Settings + Senaste Modell+Inställnings-filer + + + Set Icon Theme Ställ in Ikontema @@ -3307,12 +3488,11 @@ Starta skrivningen i alla fall ? &Inställningar - Radio Settings Profiles - Profiler för Radioinställningar + Profiler för Radioinställningar - + Invalid Models and Settings File %1 Filen innehåller inte Modeller och Inställningar: %1 @@ -3326,7 +3506,7 @@ Starta skrivningen i alla fall ? MdiChild - + @@ -3334,14 +3514,15 @@ Starta skrivningen i alla fall ? - + - - + + + @@ -3349,36 +3530,36 @@ Starta skrivningen i alla fall ? Fel - + Editing model %1: Redigera modell %1: - + Unable to find file %1! Kan inte hitta filen %1 ! - - + + Error reading file %1: %2. Fel vid inläsning från filen %1: %2. - + - + Error opening file %1: %2. Fel vid öppning av filen %1: %2. - + @@ -3404,12 +3585,12 @@ Starta skrivningen i alla fall ? %2. - + free bytes bytes lediga - + Invalid EEPROM File %1 Ogiltig modelldatafil %1 @@ -3420,48 +3601,48 @@ Starta skrivningen i alla fall ? Ogiltig binär modelldatafil %1 - + %1 has been modified. Do you want to save your changes? %1 har förändrats. Vill du spara förändringarna? - + Cannot write temporary file! En temporär fil kunde inte skrivas! - + Backup is impossible Säkerhetskopierin kan ej utföras - + - + Companion Companion - + The backup dir set in preferences does not exist Den katalog som konfigurerats för säkerhetskopiering existerar inte - - - + + + Backup EEPROM From Tx Säkerhetskopiera modelldata från sändaren - + Cannot check eeprom compatibility! Continue anyway? Det går inte att veriifiera att modelldata är kompatibla. Fortsätt i alla fall? - + Warning Varning @@ -3477,9 +3658,13 @@ Vill du spara förändringarna? Firmware i flashminnet är föråldrat. Var god uppgradera! - + + Open backup Models and Settings file + Öppna Modeller och Inställningar-fil + + Open - Öppna + Öppna @@ -3487,16 +3672,16 @@ Vill du spara förändringarna? Den binära backupfilen är felaktig %1 - - - + + + Taranis radio not found Taranis-sändaren hittades ej - - - + + + Impossible to identify the radio on your system, please verify the eeprom disk is connected. Det går inte att identifiera sändaren. Verifiera att EEPOROM-skivan är ansluteten. @@ -3506,7 +3691,7 @@ Vill du spara förändringarna? Skriv EEPROM till sändaren - + Do you want to use model wizard? Vill du använda modell-guiden? @@ -4295,7 +4480,7 @@ p, li { white-space: pre-wrap; } ModulePanel - + Trainer Output TrainerUttag @@ -4313,7 +4498,7 @@ p, li { white-space: pre-wrap; } QObject - + P1 @@ -4359,17 +4544,15 @@ p, li { white-space: pre-wrap; } T2 - th9x - th9x + th9x - er9x - er9x + er9x - + Trainer Trainer @@ -4457,10 +4640,8 @@ p, li { white-space: pre-wrap; } Timer2 - - - - + + Warning Varning @@ -4470,19 +4651,16 @@ p, li { white-space: pre-wrap; } Modelldata sparades, men med dessa varningar: - ersky9x - ersky9x + ersky9x - - - + Simulator for this firmware is not yet available Det finns ännu ingen simulator för denna typ av firmware - + REa @@ -4738,7 +4916,7 @@ p, li { white-space: pre-wrap; } PPM%1 - + THR GAS @@ -4972,7 +5150,7 @@ p, li { white-space: pre-wrap; } Det går inte att använda Expo på en specialkurva i open9x - + Support for frsky telemetry mod Stöd för FrSky telemeri @@ -5088,12 +5266,12 @@ p, li { white-space: pre-wrap; } Stöd för FrSky PXX-protokoll - + OpenTX for FrSky Taranis Rev4a OpenTX för FrSky Taranis Rev4a - + @@ -5232,21 +5410,21 @@ p, li { white-space: pre-wrap; } X%1 - + + - GV%1 GV%1 - - + + --- ---- - + Rud Trim Rod.Trim @@ -5316,8 +5494,8 @@ p, li { white-space: pre-wrap; } Eget värde - - + + -GV%1 -GV%1 @@ -5334,18 +5512,18 @@ p, li { white-space: pre-wrap; } - + PPM values displayed in us PPM-värden visade i ms - + Bluetooth interface Blåtandsinterface - - + + S1 S1 @@ -5697,7 +5875,7 @@ p, li { white-space: pre-wrap; } Ökning - + Yellow Gul @@ -5933,7 +6111,7 @@ p, li { white-space: pre-wrap; } !Kurva(%1) - + FM%1 FM%1 @@ -5983,6 +6161,11 @@ p, li { white-space: pre-wrap; } Portuguese Portugisiska + + + Finnish + Finska + !Flight mode %1 @@ -5999,7 +6182,7 @@ p, li { white-space: pre-wrap; } Flygläge %1 värde - + openTx only accepts %1 points in all curves openTX accepterar bar %1 punkter i alla kurvor @@ -6023,14 +6206,14 @@ p, li { white-space: pre-wrap; } OpenTX accepterar inte detta antal kanaler - + Your radio probably uses a wrong firmware, eeprom size is 4096 but only the first 2048 are used Din sändare har antagligen laddats med felaktig programvara. eeprom-storleken är 4096, men enbart den första hälften används - + Support for MAVLINK devices Stöd för MAVLINK-enheter @@ -6063,12 +6246,12 @@ eeprom-storleken är 4096, men enbart den första hälften används - + Use alternative SQT5 font Använd SQT5-typsnittet - + @@ -6121,24 +6304,24 @@ eeprom-storleken är 4096, men enbart den första hälften används - + Disable HELI menu and cyclic mix support Slå av HELI-menyn och stöd för cykliska mixar - - + + Disable TEMPLATES menu Slå av menyn för Mallar - - + + Disable Global variables Slå av Globala Variabler - + Possibility to enable FAI MODE at field Möjlighet att slå på FAI-LÄGE före pflygning @@ -6181,7 +6364,7 @@ Gruppen bakom OpenTX/Companion. Använd trim från flygläge %1 + Eget trim som offset - + FW: %1 FW: %1 @@ -6342,6 +6525,296 @@ Gasen reverseras om alternativet väljs. Tomgång ligger då uppåt. Trim och ga Automatiska + + SimulatorDialog + + + + Warning + Varning + + + + Joystick enabled but not configured correctly + Joysticken påslagen, men ej rätt inställd + + + + Cannot open joystick, joystick disabled + Joysticken kan inte hittas. Joysticken stängs av + + + + Simulating Tx (%1) + Simulerar sändare (%1) + + + + Firmware %1 error: %2 + Firmware %1 fel: %2 + + + + SimulatorDialog9X + + + Companion Simulator + Companion Simulator + + + + + + + Right Double Click to Reset + Höger dubbelklick nollställer + + + + THR + GAS + + + + RUD + ROD + + + + ELE + HÖJ + + + + AIL + SKE + + + + + Hold X + Håll X + + + + + Fix X + Fixera X + + + + + Fix Y + Fixera Y + + + + + Hold Y + Håll Y + + + + + + + TextLabel + Textettikett + + + + TRN + TRN + + + + GEA + LAN + + + + ID0 + ID0 + + + + ID1 + ID1 + + + + ID2 + ID2 + + + + BEEP + Summer + + + + P1 + P1 + + + + + + 0 % + 0 % + + + + P2 + P2 + + + + P3 + P3 + + + + 9x Simulator + Simulator för 9x + + + + Outputs + Utgångar + + + + SimulatorDialogTaranis + + + Companion Simulator + Companion Simulator + + + + + Hold Y + Håll Y + + + + + Fix Y + Fixera Y + + + + + Fix X + Fixera X + + + + + Hold X + Håll X + + + + + SD + SD + + + + + SC + SC + + + + + + + Right Double Click to Reset + Höger dubbelklick nollställer + + + + + S2 + S2 + + + + + SG + SG + + + + + RS + RS + + + + + SH + SH + + + + + + + TextLabel + Textettikett + + + + + S1 + S1 + + + + + SB + SB + + + + + SA + SA + + + + + SE + SE + + + + + + SF + SF + + + + + LS + LS + + + + Taranis Simulator + Taranissimulator + + + + Outputs + Utgångar + + Telemetry @@ -6685,7 +7158,7 @@ Gasen reverseras om alternativet väljs. Tomgång ligger då uppåt. Trim och ga mAmpere (mA) - + Range Räckvidd @@ -6741,7 +7214,7 @@ Gasen reverseras om alternativet väljs. Tomgång ligger då uppåt. Trim och ga Telemetriskärm %1 - + Winged Shadow How High Winged Shadow How High @@ -6809,7 +7282,7 @@ Gasen reverseras om alternativet väljs. Tomgång ligger då uppåt. Trim och ga Programmets Inställningar - + Simulator capture folder Lagra simulatorbilder i @@ -6822,27 +7295,37 @@ Gasen reverseras om alternativet väljs. Tomgång ligger då uppåt. Trim och ga - + Open Folder Öppna katalog - + User Splash Screens Egna Startbilder - + Edit Settings Redigera Inställningar - + Application Settings Programmet - + + Only show user splash images + Enbart användarens bilder + + + + Show user and companion splash images + Både användarens bilder och Companion-bilder + + + Simulator Settings Simulatorn @@ -6872,12 +7355,11 @@ Gasen reverseras om alternativet väljs. Tomgång ligger då uppåt. Trim och ga Gul - Radio Settings - Radion + Radion - + Mode selection: Mode 1: @@ -7067,17 +7549,21 @@ Detta används av mallen för att koppla kanal till output-nummer. S G H R - + Default Stick Mode Spaktilldelning - - Settings Profile - Profil + + Firmware File + Firmware - + Settings Profile + Profil + + + Splash Screen Startbild @@ -7097,42 +7583,54 @@ Detta används av mallen för att koppla kanal till output-nummer. Sökväg till SD-struktur - + + Firmware Variant + Firmware-typ + + + Select Image Välj Bild - + Offer to write FW to Tx after download Skriv FW till Tx efter nedladdning - + + Radio Settings Profile + Radioprofile + + + + Profile Name + Profilnamn + + + Remove Profile Ta bort Profil - + Clear Image Ta bort Bild - Firmware - Firmware + Firmware - Include companion splashes - Användarens bilder och Companion-bilder + Användarens bilder och Companion-bilder - Only user defined splashes - Enbart användarens bilder + Enbart användarens bilder - + Splash Screen Library Bibliotek för startbilder @@ -7207,38 +7705,38 @@ Detta används av mallen för att koppla kanal till output-nummer. Säkerhetskopiera innan firmware-skrivning - + Select your snapshot folder Välj katalog för snapshots av Tx-simulatorn - - + + No joysticks found Ingen joystick hittades - + Select your library folder Välj bibliotekskatalog - + Select your Models and Settings backup folder Välj folder för automatisk säkerhetskopiering - + Select Google Earth executable Sökväg till Google Earth - + Select the folder replicating your SD structure Välj katalog med en kopia av din SD-struktur - + Not possible to remove profile Det går inte att ta bort profilen @@ -7256,7 +7754,7 @@ Detta används av mallen för att koppla kanal till output-nummer. Det går inte att ladda %1. - + Open Image to load Öppna bild för laddning @@ -7531,7 +8029,7 @@ OBS. Fyll enbart i detta fällt om du är säker på vad du gör. Ingen kontroll Sökväg till AVRDUDE - + Select Location @@ -7617,7 +8115,7 @@ m2560 för v4.1-kort Inställningar för Programmerare - + DFU-UTIL Configuration Inställningar för DFU-UTIL @@ -7632,7 +8130,7 @@ m2560 för v4.1-kort Inställningar för AVRDUDE - + Companion Companion @@ -7646,12 +8144,12 @@ m2560 för v4.1-kort Välj Sändarens Startbild - + Date & Time Dag & Tid - + SVN Subversion @@ -7661,102 +8159,95 @@ m2560 för v4.1-kort Tillåter Companon att skriva till äldre firmware-versioner - Load Image - Ladda Bild + Ladda Bild - Open Splash Library - Öppna bildbibliotek + Öppna bildbibliotek - ... - ... + ... - Substitute image in firmware - Byt ut bilden i firmware-filen + Byt ut bilden i firmware-filen - - + Write to TX Skriv till sändaren - Use image in settings - Använd bilden från inställningarna + Använd bilden från inställningarna - Invert Color - Invertera Bilden + Invertera Bilden - + Check Firmware compatibility Kontrollera att firmware-filen är kompatibel - + Cancel Avbryt - + Write firmware to TX Skriv firmware till sändaren - Open - Öppna + Öppna - - + + - - + + Warning Varning - Burn anyway ! - Starta bränningen! + Starta bränningen! - Open Image to load - Öppna bilden som skall laddas + Öppna bilden som skall laddas - + Images (%1) Bilder (%1) - + - - - + + + + + + Error Fel - + Write Models and Settings to TX Skriv Modeller och Inställningar till sändaren @@ -7766,25 +8257,23 @@ m2560 för v4.1-kort Skriv Modeller och Inställningar från %1 till sändaren - + Choose file to load Models and Settings from Välj fil att ladda Modeller och Inställningar från - + Invalid binary Models and Settings File %1, Proceed anyway ? Ogiltig binärfil med Modeller och Inställningar: %1. Fortsätt i alla fall ? - - Cannot load %1. - Det går inte att ladda %1. + Det går inte att ladda %1. - + Cannot save customized firmware Det gick inte att spara den modifierade firmware-filen @@ -7794,12 +8283,12 @@ m2560 för v4.1-kort Bildfilen hittades inte - + No firmware selected Ingen firmware har valts - + Wrong radio calibration data in profile, Settings not patched Felaktig information i profilen, sändarens-kalibrering kunde inte läsas in @@ -7809,12 +8298,11 @@ m2560 för v4.1-kort Felaktig information i profilen, sändarens inställningar kunde inte läsas in - %1 is not a known firmware - %1 är inte en fimware-fil + %1 är inte en fimware-fil - + <html><head/><body><p>Modify calibration parameters using settings from current profile</p></body></html> <html><head/><body><p>Uppdatera kalibrerings-parametrarna med data från nuvarande profil</p></body></html> @@ -7834,8 +8322,8 @@ m2560 för v4.1-kort Uppdatera med HW-inställningar från profilen - - + + Browse for file Välj fil @@ -7850,12 +8338,42 @@ m2560 för v4.1-kort Nuvarande Profil - + + Use firmware start screen + Använd firmware-startskärmen + + + + Use another start screen + Använd en annan startskärm + + + + Use profile start screen + Använd profilens startskärm + + + + Use library start screen + Använd biblioteks-startskärm + + + Current profile Nuvarande profil - + + Open Firmware File + Öppna firmware-fil + + + + %1 may not be a valid firmware file + %1 är kanske inte en giltig firmware-fil + + + Unable to find file %1! Kan inte hitta filen %1 ! @@ -7876,7 +8394,37 @@ m2560 för v4.1-kort %2. - + + The firmware file is not valid. + Firmware-filen är inte giltig. + + + + There is no start screen image in the firmware file. + Firmware-filen innehåller inte någon startbild. + + + + The profile image %1 does not contain an image. + Profil-bilden %1 innehåller inte någon startbild. + + + + Open image file to use as Tx start screen + Öppna bildfil för användning som radions startsskärm + + + + Image could not be loaded from %1 + Det gick inte att ladda en bild från %1 + + + + The library image could not be loaded + Bild-biblioteket kunde inte öppnas + + + Cannot write file %1: %2. @@ -7891,7 +8439,7 @@ m2560 för v4.1-kort %2. - + Variant Variant @@ -7899,12 +8447,16 @@ m2560 för v4.1-kort compareDialog - Dialog - Dialog + Dialog - + + Compare Models + Jämför Modeller + + + Drag first model here Dra hit första modellen @@ -7929,7 +8481,7 @@ m2560 för v4.1-kort Skriv till fil - + General Model Settings Generella modell-inställningar @@ -8418,7 +8970,7 @@ m2560 för v4.1-kort Dialog - + People who have contributed to this project De som har bidragit till detta projekt @@ -8428,12 +8980,12 @@ m2560 för v4.1-kort Programmerare - + Companion Release Notes Companion Release Notes - + Thank you all !!! Tack till er alla !!! @@ -8448,7 +9000,7 @@ m2560 för v4.1-kort Bidragande - + OpenTX Release Notes OpenTX Release Notes @@ -8461,58 +9013,66 @@ m2560 för v4.1-kort Startbildsredigerare - - + + Invert Invertera - - + + Load FW Ladda FW - - + + Load Pict Ladda Bild - - + + Load Profile Ladda Profil - - + + Save Spara - - + + Open Splash Library Öppna bildbibliotek - Open - Öppna + Öppna - + - + Error Fel - Cannot load embedded FW image from %1. - Det gick inte att ladda bild från FW-filen %1. + Det gick inte att ladda bild från FW-filen %1. + + + + Open Firmware File + Öppna firmware-fil + + + + Can not load embedded image from firmware file %1. + Det gick inte att ladda bild från firmware-filen %1. @@ -8525,7 +9085,7 @@ m2560 för v4.1-kort Det gick inte att ladda profilbilden %1. - + Cannot load the library image %1. Det gick inte att ladda biblioteks-bilden %1. @@ -8564,7 +9124,7 @@ m2560 för v4.1-kort Det finns ingen bild att byta i firmware-filen - + Open Image to load Öppna bild för laddning @@ -8586,9 +9146,10 @@ m2560 för v4.1-kort Det gick inte att spara bilden i filen %1 - - - + + + + ... ... @@ -8601,7 +9162,7 @@ m2560 för v4.1-kort Nedladdning: - + Unable to save the file %1: %2. Kan ej spara filen %1: %2. @@ -8624,7 +9185,7 @@ m2560 för v4.1-kort Säkringar - + Read Fuses Läs in säkringarna @@ -8760,7 +9321,12 @@ p, li { white-space: pre-wrap; } fwPreferencesDialog - + + Downloads + Nedladdningar + + + @@ -8907,16 +9473,15 @@ Används av mallarna för att koppla ihop kanaler med numrerade utgångar.Skriv FW till Tx efter nedladdning - Downloads and Profiles - Nedladdning och Profiler + Nedladdning och Profiler Save Profile Spara Profil - + Menu Language Menyspråk @@ -8967,7 +9532,7 @@ Används av mallarna för att koppla ihop kanaler med numrerade utgångar.Sök efter uppdateringar - + Last downloaded release: %1 Senast nedladdade release: %1 @@ -9009,7 +9574,7 @@ Används av mallarna för att koppla ihop kanaler med numrerade utgångar. joystickDialog - + Configure Joystick Ställ in Joystick @@ -9158,7 +9723,7 @@ Används av mallarna för att koppla ihop kanaler med numrerade utgångar.OK - + Move sticks and pots in every direction making full movement Press next when finished Rör spakar och pottentiometrar. Ge fulla utslag. @@ -9209,7 +9774,7 @@ Tryck på Avbryt för att avburyta kalibreringen Dubblerad koppling av spak - + @@ -9241,7 +9806,7 @@ Tryck på Avbryt för att avburyta kalibreringen Companion Logg-läsare - + Filename Filnamn @@ -9251,7 +9816,7 @@ Tryck på Avbryt för att avburyta kalibreringen Öppna Loggfil - + Zoom Zoom @@ -9266,7 +9831,7 @@ Tryck på Avbryt för att avburyta kalibreringen Y - + Telemetry logs Telemetriloggar @@ -9276,7 +9841,7 @@ Tryck på Avbryt för att avburyta kalibreringen Tid - + Error Fel @@ -9288,7 +9853,7 @@ Tryck på Avbryt för att avburyta kalibreringen %2. - + Select your log file Välj loggfil @@ -9311,7 +9876,7 @@ Tryck på Avbryt för att avburyta kalibreringen mdiChild - + Simulate Tx Simulera sändare @@ -9324,7 +9889,7 @@ Tryck på Avbryt för att avburyta kalibreringen Guide för modellkonfiguaration - + Engine Motor @@ -9738,7 +10303,7 @@ Tryck på Avbryt för att avburyta kalibreringen Dubbla Sidoroder (med 2 servon) - + Apply configuration ? Tillämpa inställningarna? @@ -10155,62 +10720,48 @@ Mode 4: Firmware-info - Last downloaded release: %1 - Senast nedladdade release: %1 + Senast nedladdade release: %1 - - No joysticks found - Ingen joystick hittades + Ingen joystick hittades - Select your Models and Settings backup folder - Välj folder för automatisk säkerhetskopiering + Välj folder för automatisk säkerhetskopiering - Select Google Earth executable - Sökväg till Google Earth + Sökväg till Google Earth - Open Image to load - Öppna bild för laddning + Öppna bild för laddning - Images (%1) - Bilder (%1) + Bilder (%1) - - Error - Fel + Fel - The selected firmware has never been downloaded by Companion. - Firmware-filen har aldrig laddats ned av Companion. + Firmware-filen har aldrig laddats ned av Companion. - The selected firmware cannot be downloaded by Companion. - Firmware-filen kan inte laddas ned av Companion. + Firmware-filen kan inte laddas ned av Companion. - - Cannot load %1. - %1 kunde inte laddas. + %1 kunde inte laddas. - Image stored in settings - Bilden lagras i inställningar + Bilden lagras i inställningar @@ -10261,12 +10812,11 @@ Mode 4: säkerhetskopiera innan skrivning - Select your library folder - Välj bibliotekskatalog + Välj bibliotekskatalog - + Export Profile Exportera Profil @@ -10293,19 +10843,16 @@ May be different from firmware language Får skilja från språket för mjukvaran - Export profile As - Exportera profil som + Exportera profil som - Profile slot is not empty, profile slot %1 will we overwritten.<br>Are you sure ? - Det finns redan en profil i position %1,. Den kommer att skrivas över.<br> Är du säker ? + Det finns redan en profil i position %1,. Den kommer att skrivas över.<br> Är du säker ? - Open Profile to import - Öppna profil för import + Öppna profil för import @@ -10331,14 +10878,12 @@ Får skilja från språket för mjukvaran Använd bara clipboard - Select your snapshot folder - Välj katalog för snapshots + Välj katalog för snapshots - Profile name is empty, profile slot %1 will be deleted.<br>Are you sure ? - Profilnamn saknas, profilplats %1 kommer att raderas.<br> Är du säker? + Profilnamn saknas, profilplats %1 kommer att raderas.<br> Är du säker? @@ -10361,9 +10906,8 @@ Får skilja från språket för mjukvaran Sökväg till SD-struktur - Select the folder replicating your SD structure - Välj katalog som härmar din SD-struktur + Välj katalog som härmar din SD-struktur @@ -10374,7 +10918,7 @@ Får skilja från språket för mjukvaran Dialog - + Close Stäng @@ -10389,7 +10933,7 @@ Får skilja från språket för mjukvaran Skriv till fil - + Setup for: Inställningar för: @@ -10816,434 +11360,327 @@ Får skilja från språket för mjukvaran simulatorDialog - P1 - P1 + P1 - P2 - P2 + P2 - P3 - P3 + P3 - THR - GAS + GAS - RUD - ROD + ROD - ELE - HÖJ + HÖJ - AIL - SKE + SKE - - Hold X - Håll X + Håll X - - Fix X - Fixera X + Fixera X - - Fix Y - Fixera Y + Fixera Y - - Hold Y - Håll Y + Håll Y - - - - TextLabel - Textettikett + Textettikett - TRN - TRN + TRN - GEA - LAN + LAN - ID0 - ID0 + ID0 - ID1 - ID1 + ID1 - ID2 - ID2 + ID2 - BEEP - Summer + Summer - - - - Right Double Click to Reset - Höger dubbelklick nollställer + Höger dubbelklick nollställer - Companion Simulator - Companion Simulator + Companion Simulator - 9x Simulator - Simulator för 9x + Simulator för 9x - Outputs - Utgångar + Utgångar - LS1 - LB1 + LB1 - LS2 - LB2 + LB2 - LS3 - LB3 + LB3 - LS4 - LB4 + LB4 - LS5 - LB5 + LB5 - LS6 - LB6 + LB6 - LS7 - LB7 + LB7 - LS8 - LB8 + LB8 - LS9 - LB9 + LB9 - LSA - LBA + LBA - LSB - LBB + LBB - LSC - LBC + LBC - LSD - LBD + LBD - LSE - LBE + LBE - LSF - LBF + LBF - LSG - LBG + LBG - LSH - LBH + LBH - LSI - LBI + LBI - LSJ - LBJ + LBJ - LSK - LBK + LBK - LSL - LBL + LBL - LSM - LBM + LBM - LSN - LBN + LBN - LSO - LBO + LBO - LSP - LBP + LBP - LSQ - LBQ + LBQ - LSR - LBR + LBR - LSS - LBS + LBS - LST - LBT + LBT - LSU - LBU + LBU - LSV - LBV + LBV - LSW - LBW + LBW - CH1 - KN1 + KN1 - CH9 - KN9 + KN9 - CH2 - KN2 + KN2 - CH10 - KN10 + KN10 - CH3 - KN3 + KN3 - CH11 - KN11 + KN11 - CH4 - KN4 + KN4 - CH12 - KN12 + KN12 - CH5 - KN5 + KN5 - CH13 - KN13 + KN13 - CH6 - KN6 + KN6 - CH14 - KN14 + KN14 - CH7 - KN7 + KN7 - CH15 - KN15 + KN15 - CH8 - KN8 + KN8 - CH16 - KN16 + KN16 - - - - - - - - - - - - - - - - -100.1 - -100.1 + -100.1 - - Warning - Varning + Varning - Joystick enabled but not configured correctly - Joysticken påslagen, men ej rätt inställd + Joysticken påslagen, men ej rätt inställd - Cannot open joystick, joystick disabled - Joysticken kan inte hittas. Joysticken stängs av + Joysticken kan inte hittas. Joysticken stängs av - Firmware %1 error: %2 - Firmware %1 fel: %2 + Firmware %1 fel: %2 - Simulating Tx (%1) - Simulerar sändare (%1) + Simulerar sändare (%1) - Simulating - Simulerar + Simulerar - - - 0 % - 0 % + 0 % - - Flight mode: %1(%2) - - Fligmod: %1(%2) + - Fligmod: %1(%2) splashLibrary - - + + ... ... @@ -11253,7 +11690,7 @@ Får skilja från språket för mjukvaran Bildbibliotek - Sida %1 av %2 - + Warning Varning @@ -11276,428 +11713,312 @@ Får skilja från språket för mjukvaran xsimulatorDialog - - SE - SE + SE - - SA - SA + SA - - SB - SB + SB - - - - Right Double Click to Reset - Höger dubbelklick nollställer + Höger dubbelklick nollställer - - - - TextLabel - Textettikett + Textettikett - - Hold X - Håll X + Håll X - - Fix X - Fixera X + Fixera X - - Fix Y - Fixera Y + Fixera Y - - Hold Y - Håll Y + Håll Y - - SH - SH + SH - - SG - SG + SG - Companion Simulator - Companion Simulator + Companion Simulator - - SD - SD + SD - - SC - SC + SC - Outputs - Utgångar + Utgångar - CH1 - KN1 + KN1 - - - - - - - - - - - - - - - - -100.1 - -100.1 + -100.1 - CH9 - KN9 + KN9 - CH2 - KN2 + KN2 - CH10 - KN10 + KN10 - CH3 - KN3 + KN3 - CH11 - KN11 + KN11 - CH4 - KN4 + KN4 - CH12 - KN12 + KN12 - CH5 - KN5 + KN5 - CH13 - KN13 + KN13 - CH6 - KN6 + KN6 - CH14 - KN14 + KN14 - CH7 - KN7 + KN7 - CH15 - KN15 + KN15 - CH8 - KN8 + KN8 - CH16 - KN16 + KN16 - LSK - LBK + LBK - LSC - LBC + LBC - LSD - LBD + LBD - LS7 - LB7 + LB7 - LSL - LBL + LBL - LSB - LBB + LBB - LS1 - LB1 + LB1 - LSH - LBH + LBH - LSG - LBG + LBG - LSE - LBE + LBE - LSF - LBF + LBF - LS8 - LB8 + LB8 - LS9 - LB9 + LB9 - LSA - LBA + LBA - LSM - LBM + LBM - LSJ - LBJ + LBJ - LSI - LBI + LBI - LS4 - LB4 + LB4 - LS5 - LB5 + LB5 - LS2 - LB2 + LB2 - LS3 - LB3 + LB3 - LS6 - LB6 + LB6 - LSN - LBN + LBN - LSO - LBO + LBO - LSP - LBP + LBP - LSQ - LBQ + LBQ - LSR - LBR + LBR - LSS - LBS + LBS - LST - LBT + LBT - LSU - LBU + LBU - LSV - LBV + LBV - LSW - LBW + LBW - - Warning - Varning + Varning - Joystick enabled but not configured correctly - Joysticken påslagen, men ej rätt inställd + Joysticken påslagen, men ej rätt inställd - Cannot open joystick, joystick disabled - Joysticken kan inte hittas. Joysticken stängs av + Joysticken kan inte hittas. Joysticken stängs av - Firmware %1 error: %2 - Firmware %1 fel: %2 + Firmware %1 fel: %2 - Simulating Tx (%1) - Simulerar sändare (%1) + Simulerar sändare (%1) - Simulating - Simulerar + Simulerar - - - SF - SF + SF - - S2 - S2 + S2 - - RS - RS + RS - - S1 - S1 + S1 - - LS - LS + LS - Taranis Simulator - Taranissimulator + Taranissimulator - - Flight mode: %1(%2) - - Fligmod: %1(%2) + - Fligmod: %1(%2) From bfb5f5b993812708f943c0773b7fd2d49ed8ef14 Mon Sep 17 00:00:00 2001 From: Kjell Kernen Date: Tue, 25 Feb 2014 19:09:21 +0100 Subject: [PATCH 68/89] Martin Hotar splash screen in 212x64 format added --- companion/src/images/library/00005.png | Bin 209 -> 5422 bytes 1 file changed, 0 insertions(+), 0 deletions(-) diff --git a/companion/src/images/library/00005.png b/companion/src/images/library/00005.png index 802e9885a8d41bc2573134d0c875e5e07a120834..34e83f86014b84c8cd9c26ebfa5bd22486d852b6 100644 GIT binary patch delta 5418 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 U?vg>B0000907*qoM6N<$f?VRZtpET3 literal 209 zcmeAS@N?(olHy`uVBq!ia0vp^SAf`o14uBqJF!g!Qk(@Ik;M!Q+`=Ht$S`Y;1W=H@ z#M9T6{T`D94;$Owbqp3jA<+`oh!W@g+}zZ>5{8h(qQtz+Vg=9K#Pn2YAJaCV0)I~z z$B>MBZ_hLGGB9v3FUbCXZhLz(o6qO-ZeFAVE%r(G8SAxEHyZ+tX7F_Nb6Mw<&;$V7 C>o;ov From 4d2f8d29182856ea861afcc967538c486b58c8da Mon Sep 17 00:00:00 2001 From: Andre Bernet Date: Tue, 25 Feb 2014 19:49:21 +0100 Subject: [PATCH 69/89] Duration/delay display wasn't adapted on Taranis --- radio/src/gui/menu_model.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/radio/src/gui/menu_model.cpp b/radio/src/gui/menu_model.cpp index 5e020efae..5593cd0c6 100644 --- a/radio/src/gui/menu_model.cpp +++ b/radio/src/gui/menu_model.cpp @@ -4661,7 +4661,7 @@ void menuModelLogicalSwitches(uint8_t event) #if defined(CPUARM) // CSW duration if (cs->duration > 0) - lcd_outdezAtt(CSW_5TH_COLUMN, y, 5*cs->duration, (horz==LS_FIELD_DURATION ? attr : 0)|PREC1|LEFT); + lcd_outdezAtt(CSW_5TH_COLUMN, y, cs->duration, (horz==LS_FIELD_DURATION ? attr : 0)|PREC1|LEFT); else lcd_putsiAtt(CSW_5TH_COLUMN, y, STR_MMMINV, 0, horz==LS_FIELD_DURATION ? attr : 0); @@ -4673,7 +4673,7 @@ void menuModelLogicalSwitches(uint8_t event) } } else if (cs->delay > 0) { - lcd_outdezAtt(CSW_6TH_COLUMN, y, 5*cs->delay, (horz==LS_FIELD_DELAY ? attr : 0)|PREC1|LEFT); + lcd_outdezAtt(CSW_6TH_COLUMN, y, cs->delay, (horz==LS_FIELD_DELAY ? attr : 0)|PREC1|LEFT); } else { lcd_putsiAtt(CSW_6TH_COLUMN, y, STR_MMMINV, 0, horz==LS_FIELD_DELAY ? attr : 0); From b5c46626f91448d9601e500d4addd8382628bb6f Mon Sep 17 00:00:00 2001 From: Kjell Kernen Date: Tue, 25 Feb 2014 20:19:51 +0100 Subject: [PATCH 70/89] Another Taranis splash screen. Idea stolen from Martin. --- companion/src/images/library/00006.png | Bin 209 -> 3102 bytes 1 file changed, 0 insertions(+), 0 deletions(-) diff --git a/companion/src/images/library/00006.png b/companion/src/images/library/00006.png index 802e9885a8d41bc2573134d0c875e5e07a120834..7a9064c937edd1f2c6b0d6180bea69ba3a3d58d5 100644 GIT binary patch delta 3079 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 V6$#2s3eNxl002ovPDHLkV1mZX1?&I- literal 209 zcmeAS@N?(olHy`uVBq!ia0vp^SAf`o14uBqJF!g!Qk(@Ik;M!Q+`=Ht$S`Y;1W=H@ z#M9T6{T`D94;$Owbqp3jA<+`oh!W@g+}zZ>5{8h(qQtz+Vg=9K#Pn2YAJaCV0)I~z z$B>MBZ_hLGGB9v3FUbCXZhLz(o6qO-ZeFAVE%r(G8SAxEHyZ+tX7F_Nb6Mw<&;$V7 C>o;ov From 5ece7d99347fcc51f1c98543924dae976af7e4f3 Mon Sep 17 00:00:00 2001 From: Kjell Kernen Date: Wed, 26 Feb 2014 01:38:13 +0100 Subject: [PATCH 71/89] Moved selection of radio type from download dialog to profile tab. This was a bit tricky. --- companion/src/apppreferencesdialog.cpp | 43 +++---- companion/src/apppreferencesdialog.h | 2 +- companion/src/apppreferencesdialog.ui | 161 +++++++++++-------------- companion/src/fwpreferencesdialog.ui | 6 +- companion/src/helpers.cpp | 24 ++++ companion/src/helpers.h | 7 ++ 6 files changed, 129 insertions(+), 114 deletions(-) diff --git a/companion/src/apppreferencesdialog.cpp b/companion/src/apppreferencesdialog.cpp index 96f5268c3..17787f9c0 100644 --- a/companion/src/apppreferencesdialog.cpp +++ b/companion/src/apppreferencesdialog.cpp @@ -60,13 +60,22 @@ void appPreferencesDialog::writeValues() g.profile[g.id()].defaultMode(ui->stickmodeCB->currentIndex()); g.profile[g.id()].renameFwFiles(ui->renameFirmware->isChecked()); g.profile[g.id()].burnFirmware(ui->burnFirmware->isChecked()); - g.profile[g.id()].name(ui->profileNameLE->text()); g.profile[g.id()].sdPath(ui->sdPath->text()); g.profile[g.id()].splashFile(ui->SplashFileName->text()); - g.profile[g.id()].fwName(ui->fwNameLE->text()); - g.profile[g.id()].fwType(ui->fwTypeLE->text()); - - saveProfile(); + + // The profile name may NEVER be empty + if (ui->profileNameLE->text().isEmpty()) + g.profile[g.id()].name(tr("My Radio")); + else + g.profile[g.id()].name(ui->profileNameLE->text()); + + // If a new radio type has been choosen, several things need to change + if ( initialRadioType != ui->radioCB->currentIndex()) + { + g.profile[g.id()].fwName(""); + g.profile[g.id()].fwType(getDefaultFwType(ui->radioCB->currentIndex())); + current_firmware_variant = GetFirmwareVariant(g.profile[g.id()].fwType()); + } } void appPreferencesDialog::on_snapshotPathButton_clicked() @@ -146,10 +155,11 @@ void appPreferencesDialog::initSettings() ui->renameFirmware->setChecked(g.profile[g.id()].renameFwFiles()); ui->sdPath->setText(g.profile[g.id()].sdPath()); ui->profileNameLE->setText(g.profile[g.id()].name()); - ui->fwNameLE->setText(g.profile[g.id()].fwName()); - ui->fwTypeLE->setText(g.profile[g.id()].fwType()); ui->SplashFileName->setText(g.profile[g.id()].splashFile()); + initialRadioType = getRadioType(g.profile[g.id()].fwType()); + ui->radioCB->setCurrentIndex(initialRadioType); + displayImage( g.profile[g.id()].splashFile() ); } @@ -237,23 +247,6 @@ void appPreferencesDialog::on_sdPathButton_clicked() } } -void appPreferencesDialog::saveProfile() -{ - // The profile name may NEVER be empty - if (ui->profileNameLE->text().isEmpty()) - ui->profileNameLE->setText("----"); - - g.profile[g.id()].name( ui->profileNameLE->text() ); - g.profile[g.id()].channelOrder( ui->channelorderCB->currentIndex()); - g.profile[g.id()].defaultMode( ui->stickmodeCB->currentIndex()); - g.profile[g.id()].burnFirmware( ui->burnFirmware->isChecked()); - g.profile[g.id()].renameFwFiles( ui->renameFirmware->isChecked()); - g.profile[g.id()].sdPath( ui->sdPath->text()); - g.profile[g.id()].splashFile( ui->SplashFileName->text()); - g.profile[g.id()].fwName( ui->fwNameLE->text()); - g.profile[g.id()].fwType( ui->fwTypeLE->text()); -} - void appPreferencesDialog::on_removeProfileButton_clicked() { if ( g.id() == 0 ) @@ -266,6 +259,7 @@ void appPreferencesDialog::on_removeProfileButton_clicked() } } + bool appPreferencesDialog::displayImage( QString fileName ) { // Start by clearing the pixmap @@ -310,3 +304,4 @@ void appPreferencesDialog::on_clearImageButton_clicked() { + diff --git a/companion/src/apppreferencesdialog.h b/companion/src/apppreferencesdialog.h index 18ce2f1e3..46bdf3156 100644 --- a/companion/src/apppreferencesdialog.h +++ b/companion/src/apppreferencesdialog.h @@ -21,10 +21,10 @@ public: Joystick *joystick; private: + int initialRadioType; Ui::appPreferencesDialog *ui; void initSettings(); bool displayImage( QString fileName ); - void saveProfile(); void loadProfileString(QString profile, QString label); void loadFromProfile(); diff --git a/companion/src/apppreferencesdialog.ui b/companion/src/apppreferencesdialog.ui index bdaaff9d4..f5d4b9deb 100644 --- a/companion/src/apppreferencesdialog.ui +++ b/companion/src/apppreferencesdialog.ui @@ -7,7 +7,7 @@ 0 0 685 - 442 + 462 @@ -26,21 +26,12 @@ Edit Settings - - 6 - - - 6 - - - 6 - - - 6 - 2 + + 6 + @@ -502,7 +493,7 @@ Radio Settings Profile - + @@ -556,7 +547,7 @@ Mode 4: - + @@ -706,7 +697,7 @@ This is used by the templated to determine which channel goes to what number out - + @@ -726,7 +717,7 @@ This is used by the templated to determine which channel goes to what number out - + Qt::Vertical @@ -739,7 +730,7 @@ This is used by the templated to determine which channel goes to what number out - + @@ -752,7 +743,7 @@ This is used by the templated to determine which channel goes to what number out - + @@ -768,14 +759,14 @@ This is used by the templated to determine which channel goes to what number out - + Append version number to FW file name - + @@ -791,7 +782,7 @@ This is used by the templated to determine which channel goes to what number out - + true @@ -813,7 +804,7 @@ This is used by the templated to determine which channel goes to what number out - + Qt::Horizontal @@ -826,35 +817,35 @@ This is used by the templated to determine which channel goes to what number out - + Offer to write FW to Tx after download - + Remove Profile - + Open Folder - + Qt::Horizontal - + true @@ -876,46 +867,34 @@ This is used by the templated to determine which channel goes to what number out - - - - Firmware Variant - - - - - - - false - - - - 350 - 0 - - - - - 350 - 16777215 - - - - - + Select Image - + + + + Radio Type + + + + Clear Image + + + + Qt::Horizontal + + + @@ -932,7 +911,7 @@ This is used by the templated to determine which channel goes to what number out - + @@ -969,37 +948,43 @@ This is used by the templated to determine which channel goes to what number out - - - - Qt::Horizontal - - - - - - - Firmware File - - - - - - - false - - - - 350 - 0 - - - - - 350 - 16777215 - - + + + + + 9X + + + + + 9X with m128 + + + + + 9XR + + + + + 9XR with m128 + + + + + Gruvin9x Board + + + + + Sky9x Board + + + + + Taranis + + diff --git a/companion/src/fwpreferencesdialog.ui b/companion/src/fwpreferencesdialog.ui index 28585c2ac..d095e2cb7 100644 --- a/companion/src/fwpreferencesdialog.ui +++ b/companion/src/fwpreferencesdialog.ui @@ -157,7 +157,11 @@ - + + + false + + diff --git a/companion/src/helpers.cpp b/companion/src/helpers.cpp index e0cd7b91c..17d908ecc 100644 --- a/companion/src/helpers.cpp +++ b/companion/src/helpers.cpp @@ -969,3 +969,27 @@ QPixmap makePixMap( QImage image, QString firmwareType ) } return(QPixmap::fromImage(image)); } + +int getRadioType(QString firmwareType) +{ + if (firmwareType.contains( "taranis" )) return 6; + if (firmwareType.contains( "sky9x" )) return 5; + if (firmwareType.contains( "gruvin9x")) return 4; + if (firmwareType.contains( "9xr128" )) return 3; + if (firmwareType.contains( "9xr" )) return 2; + if (firmwareType.contains( "9x128" )) return 1; + return 0; // 9x +} + +QString getDefaultFwType( int radioType ) +{ + switch (radioType){ + case 6: return "opentx-taranis-en"; + case 5: return "opentx-sky9x-en"; + case 4: return "opentx-gruvin9x-en"; + case 3: return "opentx-9xr128-en"; + case 2: return "opentx-9xr-en"; + case 1: return "opentx-9x128-en"; + default: return "opentx-9x-en"; + } +} diff --git a/companion/src/helpers.h b/companion/src/helpers.h index 5d667e5d8..857d66749 100644 --- a/companion/src/helpers.h +++ b/companion/src/helpers.h @@ -128,6 +128,13 @@ QString getFrSkySrc(int index); void startSimulation(QWidget * parent, RadioData & radioData, int modelIdx); +// Format a pixmap to fit on the radio using a specific firmware QPixmap makePixMap( QImage image, QString firmwareType ); +// Return a radio type derived from a firmware type string +int getRadioType(QString firmwareType); + +// Return the default firmware string for a specified radio +QString getDefaultFwType( int radioType ); + #endif // HELPERS_H From f7e741b4e2c4568ceb8a1f4f7632148496744ead Mon Sep 17 00:00:00 2001 From: Kjell Kernen Date: Wed, 26 Feb 2014 03:11:33 +0100 Subject: [PATCH 72/89] Pict upddates --- companion/src/images/library/00004.png | Bin 7521 -> 24139 bytes companion/src/images/library/00006.png | Bin 3102 -> 3097 bytes companion/src/images/library/00007.png | Bin 209 -> 1343 bytes companion/src/images/library/10702.png | Bin 529 -> 374 bytes 4 files changed, 0 insertions(+), 0 deletions(-) diff --git a/companion/src/images/library/00004.png b/companion/src/images/library/00004.png index 5982d425cb67e25dc980de353404bfa82ec9dbf5..a9c5e87162dc75220c183c3a08152cca07d188b3 100644 GIT binary patch literal 24139 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 YrWpxnLoMrrGgAmoK~4URtXbgy0Hqy2mjD0& diff --git a/companion/src/images/library/00006.png b/companion/src/images/library/00006.png index 7a9064c937edd1f2c6b0d6180bea69ba3a3d58d5..ce8bb5ce1c478b65fc2698a22c5ce7f53b45e616 100644 GIT binary patch delta 3057 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 delta 3062 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 Eg8FO%TmS$7 diff --git a/companion/src/images/library/00007.png b/companion/src/images/library/00007.png index 802e9885a8d41bc2573134d0c875e5e07a120834..14b5b77445e9242a3535546e488a6f1d5776d007 100644 GIT binary patch delta 1275 zcmVxxLP_!ErREpq2H-fHJnvFk*tD;z4xDioERA}1dbdkL4opa~jJ9F<%UhbQ7vdBGW z&iCd_PUh#Ex$_hepa2k>BHEPHh}8IhBSpn_O+}zQPr+4>(_?vS0<$zYdkU_4Tmw0x zP)r0@EiN}vRPciZS1pdsQEB5QK+)u;n6Ka_1E-shWX(He{2vHzGI5HCkDx_5r{E?U zr^n1@msAGCO%vP%GDx<5ZxKnT%?2lHA*;LuWFr756wb8IzoHo+{e|HzxfckDq=3KsSaHC10~N zyn`nRpWjoK7kTZ|p);AHatl8sY=_Wc=-aS>c|5=#HrTnwsmlxo?T*Wqe*DQSOYm(> zn~wdgd;~psRWMH7%pDb&s@olZmn|dMgqO^A5YwXP9hlEbk6@s1oSMcnY0D->StcXr z6f3Jcu8cgyPG(tzt>aI#(96p1;`@|7uFf3OL|nG5yo z_ObJ*_GeBmJc>Nn)_b^z_YKQF9Kjs?joF5EFMj5Kdaw3rcSb@5natFG#+8+4_=Z_} z(TQG`rtA3CIwQHqsg?I8qc4-0%D5`z3Qn*-wi(+E%MiZ8Xlj3UYhSd5q%7N;A!ucX zJ^<*%ZG0Tl2QkYi--462S;s3*EzGIByv9cS7t_r&UACmjKTgj?h0UDO<)&qyqB)0c zt|U%2^o95K+#I|pJ@f&8z+1S6l@|M2TudEaed5%iF(;0DF@gIOz`2w(`Nx^bqe6Il zu8PG()9V^OXSQXy=U7KxoH;zI-OsA3lwFB50mpI{0Uqs>`%%^OsO1>I+ZOwN{FG9M zU!20DDoNA~+{RLC$-h{EJE@7PkVgq~a*^XknqJ4AJMahIt)PZ~+(Zd;%9jo3G4wv; zc<>YaQbi>c9p@8K>~NnFdfX>o)*d({%HBx!OB5f{py544bLlAigfA_1_{ACc{iyQN zf%BMYSPtVke#D?*JB4`;V?tK@qN8|o5aB~g+)gog{c&Zb51$$OBm4&7Df$d+7fx9R zYmYeNosTFqt?bZ$_XUkI-}U1q)94{9*=ni7J!-ihRbqMGg}dl7EH|(!dR~VMY>$08 z{<7}%xy5NrY2j(bdz7N9%x{#s4Ug-r{3dmzE++Cc9UgP4igE468fH0zTZaA}>zm!F zhaoO;S~E$Bg`=BRKU~os^(hTAuOa#%;dPezjL>SY9u=#9KV0TiCQ&o#e!}aZ#cv_K zVqTAEcA+@sepDejfsdHwvE@A@;0b$43|Jg{6-MqyIpgGhl-!T!n^KM?G11XH3rLLh6n#VN-v-$0*D^FeYJPg<0m`s|4>$nu zw8A8ym{+JY0fw@fB|s@3qA%*BxwiJMR0zOFAG|s zmgKU+c7aOAC9@*Mu8WYiUQY|CfO40@C$JIHq4xTBy#S)^ynfVZ6FC3?002ovPDHLk FV1hhId&vL* delta 462 zcmeyyG?8V3BnJZ!{95aDX`+L8J)?rBi(`nz>8F=${SF(5Fgy@X{m}G;+29A)RHjsh zhplo4gGB{i&EYlIQDIl;;597n^*EvA?x3355u~Zi;}~h>Am^Fko2(bW*+2i@{Cma= zJ|<)@*N9-uo*XO5XIHSo;nbY$7GD5haeLB^mie42~&9nTdG{j=4#xMd@|< z;ZYMaRI*h;3Q`hFQmvAUQh^kMk%6I+u7RPhp=pSrnU$f5m5G_QfuWUw!IinP-+(3} dH00)|WTsW(*0A)zQZG={dAj Date: Wed, 26 Feb 2014 06:44:00 +0100 Subject: [PATCH 73/89] Update DONATIONS.txt --- DONATIONS.txt | 3 +++ 1 file changed, 3 insertions(+) diff --git a/DONATIONS.txt b/DONATIONS.txt index c85c6de97..46df5704e 100644 --- a/DONATIONS.txt +++ b/DONATIONS.txt @@ -327,3 +327,6 @@ Pierluigi Sommaruga Rafael Eric Suarez Nordlow A Harris Stefan Grunenberg +Francisco Gutierrez Muñoz +Steve Coley + From f5b9ebfcc3fad4c5d928b841b7e5e4622aacce5d Mon Sep 17 00:00:00 2001 From: bsongis Date: Wed, 26 Feb 2014 09:54:25 +0100 Subject: [PATCH 74/89] Core in import of EEPROMS < 216 --- companion/src/eepromimportexport.h | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-) diff --git a/companion/src/eepromimportexport.h b/companion/src/eepromimportexport.h index 91eda318c..5ea132e61 100644 --- a/companion/src/eepromimportexport.h +++ b/companion/src/eepromimportexport.h @@ -650,12 +650,14 @@ class ConversionField: public TransformedField { if (!error.isEmpty()) EEPROMWarnings += error + "\n"; } - else if (shift) { + + if (shift) { if (val < min) _field = min + shift; else if (val > max) _field = max + shift; else _field = val + shift; } - else { + + if (exportFunc) { _field = exportFunc(val); } } @@ -666,10 +668,12 @@ class ConversionField: public TransformedField { if (table->importValue(_field, field)) return; } - else if (shift) { + + if (shift) { field = _field - shift; } - else { + + if (importFunc) { field = importFunc(_field); } From d14fc31f885072661aa21fb5928a730b44d5c739 Mon Sep 17 00:00:00 2001 From: bsongis Date: Wed, 26 Feb 2014 11:21:09 +0100 Subject: [PATCH 75/89] Import bug, scale result was always 0 --- companion/src/eepromimportexport.h | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/companion/src/eepromimportexport.h b/companion/src/eepromimportexport.h index 5ea132e61..242c1f7f7 100644 --- a/companion/src/eepromimportexport.h +++ b/companion/src/eepromimportexport.h @@ -669,9 +669,7 @@ class ConversionField: public TransformedField { return; } - if (shift) { - field = _field - shift; - } + field = _field - shift; if (importFunc) { field = importFunc(_field); From f2e252c986795f182353adaefccc5d47d8b1f675 Mon Sep 17 00:00:00 2001 From: Kjell Kernen Date: Wed, 26 Feb 2014 11:23:43 +0100 Subject: [PATCH 76/89] Moved library images around to make room for a full page of Taranis screens. This makes the library look a lot better. --- companion/src/companion.qrc | 21 ++++++++++++++---- companion/src/images/library/00004.png | Bin 24139 -> 8265 bytes companion/src/images/library/00010.png | Bin 353 -> 209 bytes companion/src/images/library/00011.png | Bin 3692 -> 209 bytes companion/src/images/library/00012.png | Bin 3469 -> 209 bytes companion/src/images/library/00013.png | Bin 425 -> 209 bytes companion/src/images/library/00014.png | Bin 341 -> 209 bytes companion/src/images/library/00015.png | Bin 325 -> 209 bytes companion/src/images/library/00016.png | Bin 603 -> 209 bytes companion/src/images/library/00017.png | Bin 634 -> 209 bytes companion/src/images/library/00018.png | Bin 3760 -> 209 bytes companion/src/images/library/00019.png | Bin 451 -> 209 bytes companion/src/images/library/00020.png | Bin 764 -> 209 bytes companion/src/images/library/00050.png | Bin 0 -> 353 bytes companion/src/images/library/00051.png | Bin 572 -> 3692 bytes companion/src/images/library/00052.png | Bin 0 -> 3469 bytes companion/src/images/library/00053.png | Bin 0 -> 425 bytes companion/src/images/library/00054.png | Bin 0 -> 341 bytes companion/src/images/library/00055.png | Bin 0 -> 325 bytes companion/src/images/library/00056.png | Bin 0 -> 603 bytes companion/src/images/library/00057.png | Bin 0 -> 634 bytes companion/src/images/library/00058.png | Bin 0 -> 3760 bytes companion/src/images/library/00059.png | Bin 0 -> 451 bytes companion/src/images/library/00060.png | Bin 0 -> 764 bytes .../images/library/{00021.png => 00061.png} | Bin .../images/library/{00022.png => 00062.png} | Bin .../images/library/{00023.png => 00063.png} | Bin .../images/library/{00024.png => 00064.png} | Bin .../images/library/{00031.png => 00065.png} | Bin companion/src/images/library/00066.png | Bin 0 -> 368 bytes companion/src/images/library/10702.png | Bin 374 -> 572 bytes 31 files changed, 17 insertions(+), 4 deletions(-) create mode 100644 companion/src/images/library/00050.png create mode 100644 companion/src/images/library/00052.png create mode 100644 companion/src/images/library/00053.png create mode 100644 companion/src/images/library/00054.png create mode 100644 companion/src/images/library/00055.png create mode 100644 companion/src/images/library/00056.png create mode 100644 companion/src/images/library/00057.png create mode 100644 companion/src/images/library/00058.png create mode 100644 companion/src/images/library/00059.png create mode 100644 companion/src/images/library/00060.png rename companion/src/images/library/{00021.png => 00061.png} (100%) rename companion/src/images/library/{00022.png => 00062.png} (100%) rename companion/src/images/library/{00023.png => 00063.png} (100%) rename companion/src/images/library/{00024.png => 00064.png} (100%) rename companion/src/images/library/{00031.png => 00065.png} (100%) create mode 100644 companion/src/images/library/00066.png diff --git a/companion/src/companion.qrc b/companion/src/companion.qrc index c6246f314..dcb97f0b3 100644 --- a/companion/src/companion.qrc +++ b/companion/src/companion.qrc @@ -168,6 +168,7 @@ images/library/00009.png images/library/00010.png images/library/00011.png + images/library/00012.png images/library/00013.png images/library/00014.png images/library/00015.png @@ -176,11 +177,23 @@ images/library/00018.png images/library/00019.png images/library/00020.png - images/library/00021.png - images/library/00022.png - images/library/00023.png - images/library/00024.png + images/library/00050.png images/library/00051.png + images/library/00052.png + images/library/00053.png + images/library/00054.png + images/library/00055.png + images/library/00056.png + images/library/00057.png + images/library/00058.png + images/library/00059.png + images/library/00060.png + images/library/00061.png + images/library/00062.png + images/library/00063.png + images/library/00064.png + images/library/00065.png + images/library/00066.png images/library/00100.png images/library/00101.png images/library/00102.png diff --git a/companion/src/images/library/00004.png b/companion/src/images/library/00004.png index a9c5e87162dc75220c183c3a08152cca07d188b3..e8494d86808bb500126ec059802213b1b40521c8 100644 GIT binary patch literal 8265 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 Hu0mjf*@>m) literal 24139 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 C>o;ov delta 331 zcmV-R0kren3K!?0*#A53>RivgEhofc()wDptw+k`$ym=Xs6;!@hq^Ku%bJVvG#mg%n1G zKs$rq!Um);J;x~dP^yAWZZJrGEwe&@0_*Zp7CS*JFkm~;?w}nKL*MTBZ|fMKbvX?- z7<4v=Kh`#Sbdo!pG_2taf@KM7d;@Q3J6_KFc~XGQ3Kjazk{e*MRkk7poHWcOjH#!` di@mx20BIbu-5{8h(qQtz+Vg=9K#Pn2YAJaCV0)I~z z$B>MBZ_hLGGB9v3FUbCXZhLz(o6qO-ZeFAVE%r(G8SAxEHyZ+tX7F_Nb6Mw<&;$V7 C>o;ov literal 3692 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`!2~2@x4h5*Qf*Zs5hX#1CLR`=Ysy8gRJ$k9D1HV7KUGkyqwI>m8@}dqp{&Z|7^4S@O9&ev2rN zV)n(_9m*RMoxkzO3bRHW*jns2Z|xkA1@fA+rNF$_uczjRP5ndetVU-MOv$` z`UFM>=J%*p$~V}1On zC3`zAn+hwS0lBFqi3%0DIeEoa6}C!XbFF}Ekg&dz0$52&wyjcxZ-9bxeo?A|iJpm` zfv#&sW|@(a9hZVlQA(Oskc%7C2q4c^DWjyMz)D}gyu4hm+*mKaC|%#s($Z4jz)0W7 zNEfI=x41H|B(Xv_uUHvm1jG!N)Z*l#%z~24{5%DanTbjHr6smXNP z3=ITeaOi_%^bPe4^pTa9WTxRz4w6AA2Whqn$gD`siEzoxP0cF?I>A=S(8vO87(zA@ zN!H8+ED18m$}=}HJvBTtr6dEW3r*M~H8VW}=nbHHeNbrWLxT$#`ugzT2ZaIc!Kfu9 zh4E-`jRqGTqK16Ns32P*U$ut>KO}7kqRC@mZpZ=0L_t?=-SzGrNM*UP|ZagyS+O9P+ zJL1+~S3bV;qmQr(1E)hDivr_`i3}3I3dipSp7X1Z4gXuluWN6V89pQUa(zVN zY)ikhzg-!wsI5rfe}292$vKPE&)ah}tbX;Ido?3N@cZ^ec7}yBs$;JQG2FRnethYs zE7$Vo*lv4g^?6_X{rR(AotawfF52?;o}Pctqc5SC)Y^U@&GMYqq9Aj;dgiu$S#xiF z{p-sZbMpD@Y(a*mHQU>~885uqvCgUb-N!Gy`~En$>PuhyXT9UPyJBU-jzquZt){_O ztWAAyQaN}CXsNWjr&vLcvB*)bs^9b$;StuHj zZhwX~LAEz!rmgduv_r~!?HA~5o5akp(s**dbFKS!<2_Ogn~q;t#U>VWVn*wicLBeO zRtj&n^0>~DJ>kp*dG8JC2J0& z?6fA`BtKu2^*~I?3~hr#qbcEwkL@hgxwY20(>wdauIS@4ZuXhGJJ&`A=>JU3(744> zc}&OfdD&KzEw}n6KkJZx_h{PPdSBje8ctlv{{7D+w$~op5w$`urG+QcciFn2$Hxu_ zBufi1U6}t@_W!o+hp&4_Nv}Jry>zSQ%WXAVjxPN6Ag)()fArJ_AH54J54GgX(Q;nL zeroDVm2R$s8?w5-aoh>WG+1?TMuOLY&(4?Bow^vU4((RRh&plb_`KRboThfyclNtX zu<3Xy)FgVB+vrKNV9^Wn{eO6-_AlVQxv%e1b= zORHVd4pGhe6KY%x+Fli#o^E=6aE&Hs=7kvkG<%1~8Ol5IGTgPNMJ2SmXE?h(I9ap2 zyr$T6mafFBzNhmqU$|O!%ONaN=+Pw8%!!Kt2uK(fZ z#CXYipR0F7FWyQ|Hx&4B*J5M%u7n?v{qrK?zutCfyR_Te_gU&<2A9uI&j0ma!JFmx zg1Nr3<)+x;BeS2!Pn#?IGn|#vfoXy=qX$C~dbawX{)fq?HZk?tp8X#|T{2HsKbLh* G2~7a+5VJb~ diff --git a/companion/src/images/library/00012.png b/companion/src/images/library/00012.png index 64eca2f6622431d42cc2fe98cc671ec54334e97b..802e9885a8d41bc2573134d0c875e5e07a120834 100644 GIT binary patch literal 209 zcmeAS@N?(olHy`uVBq!ia0vp^SAf`o14uBqJF!g!Qk(@Ik;M!Q+`=Ht$S`Y;1W=H@ z#M9T6{T`D94;$Owbqp3jA<+`oh!W@g+}zZ>5{8h(qQtz+Vg=9K#Pn2YAJaCV0)I~z z$B>MBZ_hLGGB9v3FUbCXZhLz(o6qO-ZeFAVE%r(G8SAxEHyZ+tX7F_Nb6Mw<&;$V7 C>o;ov literal 3469 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`!2~2@x4h5*Qf*Zs5hX#1CLR`=Ysy8gRJ$k9D1HV7KUGkyqwI>m8@}dqp{&Z|7^4S@O9&ev2rN zV)n(_9m*RMoxkzO3bRHW*jns2Z|xkA1@fA+rNF$_uczjRP5ndetVU-MOv$` z`UFM>=J%*p$~V}1On zC3`zAn+hwS0lBFqi3%0DIeEoa6}C!XbFF}Ekg&dz0$52&wyjcxZ-9bxeo?A|iJpm` zfv#&sW|@(a9hZVlQA(Oskc%7C2q4c^DWjyMz)D}gyu4hm+*mKaC|%#s($Z4jz)0W7 zNEfI=x41H|B(Xv_uUHvm1jG!N)Z*l#%z~24{5%DanTbjHr6smXNP z3=ITeaOi_%^bPe4^pTa9WTxRz4w6AA2Whqn$gD`siEzoxP0cF?I>A=S(8vO87(zA@ zN!H8+ED18m$}=}HJvBTtr6dEW3r*M~H8VW}=nbHHeNbrWLxT$#`ugzT2ZaIc!Kfu9 zh4E-`jRqGTqK16Ns32P*U$(!%{4%=Ohe9m%cXFEE{NwI@_$E&K--4*9s zRxL1MGoKmfqi1$?Y2>xpA4?y}MsAH;duUfw?+2OOgI@XuEuD{wxmO?#~Z5CC-UzwmK!ps??>sbwl>aEW4!)Yp2?VUc7Yc z6NkL{Evwr8dgW(R|2eJR$PqdBb2#6+m@bxulNyY2?xwC#(%o|Jwm64a{_mIEl||e3 zNKaW9ohhdx7@F@Kw_HR0msCNOapkWzZKsPlr-azIyQugw-<+hhYVAyK8IOky>~?D( zF0DS_`a56i(BIz8Uf&d+exG>Q!aLf)@sCEq{fEL^-f;ImPCD>};ndkMUJjw0bI%#G z!khY1U5bi1_8Ri#wU*y_dQ?bYiTl!`&GC)iQ(p?P+ed0dZ8c_$i@s-+D(sl=vVXsW z3df(|fcV*Lu2(k*xm;$JV`bVmakNrEbpqyAOD_jerbdfXXdH0f8LW> zk1vcnzQ_56vfc4&X2w@x-XZ*QjsH$bCCuFV(Es*-e(_HqQ*J-W-r&AW;a29KbXk=K hmJ7(q&+O(u20lU0^PNAp%mk)u22WQ%mvv4FO#qlUGS2`2 diff --git a/companion/src/images/library/00013.png b/companion/src/images/library/00013.png index c73a997018e588451bdf45c8c1d740f5ab917342..802e9885a8d41bc2573134d0c875e5e07a120834 100644 GIT binary patch literal 209 zcmeAS@N?(olHy`uVBq!ia0vp^SAf`o14uBqJF!g!Qk(@Ik;M!Q+`=Ht$S`Y;1W=H@ z#M9T6{T`D94;$Owbqp3jA<+`oh!W@g+}zZ>5{8h(qQtz+Vg=9K#Pn2YAJaCV0)I~z z$B>MBZ_hLGGB9v3FUbCXZhLz(o6qO-ZeFAVE%r(G8SAxEHyZ+tX7F_Nb6Mw<&;$V7 C>o;ov delta 406 zcmV;H0crlx0jUE(iBL{Q4GJ0x0000DNk~Le0001h0000$0RsR40O%O)JOBUy22e~? zMgRZ*00010!qa{L0004EOGiWihy@);ks%&`-2@yGIVU+6q z_byhwB|{tN!$CgW-TV4HfPEC>oEN_Z!#uJ3pr1Xy?gH~zfz`VTANH_IHSDrGm<|Vj z)$mX-opuFEICKZVUe-qn)LL=LZlOYJ`h8P0z{SJ08tduTLqhPD25AuC9ga$mp!8Ee zXAvTl@{A6+>_Wf=ToJemR1N`PyJcCO|3E3fmfHFaP}>G57)N9jOw2<>Un6QF`gTm7 zdI$ah_EJgz&vh`Wn-{&ma4g_DkE}&a9^8kYad8?pFq>zyMV2McaqNwswlHtO>48fC z5+*IsmW$AuWNBhASDrW&z>rD0du7OhB=Em$0|2_oqwwh!nE(I)07*qoM6N<$f|c*5 A1^@s6 diff --git a/companion/src/images/library/00014.png b/companion/src/images/library/00014.png index e4d1878c923b1146164338789ae4317529cc06ed..802e9885a8d41bc2573134d0c875e5e07a120834 100644 GIT binary patch literal 209 zcmeAS@N?(olHy`uVBq!ia0vp^SAf`o14uBqJF!g!Qk(@Ik;M!Q+`=Ht$S`Y;1W=H@ z#M9T6{T`D94;$Owbqp3jA<+`oh!W@g+}zZ>5{8h(qQtz+Vg=9K#Pn2YAJaCV0)I~z z$B>MBZ_hLGGB9v3FUbCXZhLz(o6qO-ZeFAVE%r(G8SAxEHyZ+tX7F_Nb6Mw<&;$V7 C>o;ov delta 321 zcmV-H0lxmx0o4LPiBL{Q4GJ0x0000DNk~Le0001h0000$0RsR40O%O)JOBUy22e~? zMgRZ*00010!qa{L0004EOGiWihy@);ks%&`-2@yH1v#-PiqZf80M$uEK~y-)?b0y{ z!Y~vD;6R~S92`3cMG%jnS1ITLT3kg_I=owWmX;31saI&N=vr`TQG7P9R85u+y6GD~ zlK20CF!mp1I3i}B!oZq3?_e(Xhd!_-8q`M}PL7&VsVV)%Og604rOa}>6I>9CJOy}o zej96WH?oV{$kDFzj36)KB2FL$aR~{EsEE!%0w7j`cD!IKD1`te z%qiB>pmGTW@2-^9;t6tT^ID3H0NPmjd@2SIP%#Oz`i6rqtG8o>+8_7^{Kz~2ykn}o TndxV*00000NkvXXu0mjf@}zzh diff --git a/companion/src/images/library/00015.png b/companion/src/images/library/00015.png index 5bf13ecb2db9a290b2c6562947003a438e6da7c5..802e9885a8d41bc2573134d0c875e5e07a120834 100644 GIT binary patch literal 209 zcmeAS@N?(olHy`uVBq!ia0vp^SAf`o14uBqJF!g!Qk(@Ik;M!Q+`=Ht$S`Y;1W=H@ z#M9T6{T`D94;$Owbqp3jA<+`oh!W@g+}zZ>5{8h(qQtz+Vg=9K#Pn2YAJaCV0)I~z z$B>MBZ_hLGGB9v3FUbCXZhLz(o6qO-ZeFAVE%r(G8SAxEHyZ+tX7F_Nb6Mw<&;$V7 C>o;ov delta 305 zcmV-10nYx>0mT9{iBL{Q4GJ0x0000DNk~Le0001h0000$0RsR40O%O)JOBUy22e~? zMgRZ*00010!qa|{As&C-1REC$B+qGTp#T5?(n&-?R5;7E)4>VDAQT2*_0dNATz&)S3{8zmlYd_CX+gV0`}OG4@IEu$12fy}X<^;khh% z{1i;b9Lf6%x@9*K3DlSN8fb-~sUq+k7(o0669A4*0Lq0bhdOl!DbhYBfKC;*Zn_M< z&tr&>QCcA(0|I9VA^s)^nvTGT46HnYVo3qTE=6NJ zgW_-_>3%5{8h(qQtz+Vg=9K#Pn2YAJaCV0)I~z z$B>MBZ_hLGGB9v3FUbCXZhLz(o6qO-ZeFAVE%r(G8SAxEHyZ+tX7F_Nb6Mw<&;$V7 C>o;ov delta 586 zcmV-Q0=50o0ow#2iBL{Q4GJ0x0000DNk~Le0001h0000$2m$~A09~}`D3Ku^f87Ke z6B{PzV7T}I00H_*L_t(|+U=X!lEfegMMum3|7GVPQ$1ZBTY-RPIrrHGIYq5_Z1MJ{j+?HI)>^GXMYx002M$0006201yBGfB^6umD{h- zeCN8=%f5AQ7XDO?*#VPC_iMBOe-P~h^Trxh$N}Ks#3P9=KgUP&pDq%sioAbkzRpY^ zz4|t7jo;feCv7%JDb-qoNNj_vNC+({a)Ab+ zv3Z>(ymrrW@5>Fy+LY~*f73%Z!Tijlx}KE2h&4+$XZWXe7#|Vdk4Qd$gWTgk;a92L ze0yccw~}|A;js6)lAIa)^6($VcfO7HPqGW`r=Sb{;Wo|n+VD5rn(5{8h(qQtz+Vg=9K#Pn2YAJaCV0)I~z z$B>MBZ_hLGGB9v3FUbCXZhLz(o6qO-ZeFAVE%r(G8SAxEHyZ+tX7F_Nb6Mw<&;$V7 C>o;ov delta 614 zcmV-s0-62M0r~_$iBL{Q4GJ0x0000DNk~Le0001h0000$0RsR40O%O)JOBUy22e~? zMgRZ*00010!qa{L0004EOGiWihy@);ks%>}2{Qs7ImCPb00H_*L_t(I%e|99i<>|g zhCdPFCGFgbg>Lc(dN2fR7u@u($Og1kDT=ovtbZru$vw_GThr?df*nTOttL+sSu- zO9Xwcq63mxydL1p6pQon?48@sWV}%YrX7x5?2Yc`jVgZa~347%G?Z)llS#t6uNkyv% z0+6fw@ZQ`d{znQNg#x{s_$CEG1>(c@ZZjIi)fxf8JB`O-{KI$^PY|U2VhkXEV+{>J zL6G$e8MJfk@mkgB3{sp6Kk7C9>``ya#Grr`V`5Z5ssI-Q*LakrvhibA0jF&IxXMYP zIHe=*1AF93Fl+gdlZ*t$q1_`R=~>Hh5FI?1poj507*qoM6N<$f;M6n AzyJUM diff --git a/companion/src/images/library/00018.png b/companion/src/images/library/00018.png index fa384d1e69d6717e7dc37c1f73537364befb0c16..802e9885a8d41bc2573134d0c875e5e07a120834 100644 GIT binary patch literal 209 zcmeAS@N?(olHy`uVBq!ia0vp^SAf`o14uBqJF!g!Qk(@Ik;M!Q+`=Ht$S`Y;1W=H@ z#M9T6{T`D94;$Owbqp3jA<+`oh!W@g+}zZ>5{8h(qQtz+Vg=9K#Pn2YAJaCV0)I~z z$B>MBZ_hLGGB9v3FUbCXZhLz(o6qO-ZeFAVE%r(G8SAxEHyZ+tX7F_Nb6Mw<&;$V7 C>o;ov literal 3760 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`!2~2@x4h5*Qf*Zs5hX#1CLR`=Ysy8gRJ$k9D1HV7KUGkyqwI>m8@}dqp{&Z|7^4S@O9&ev2rN zV)n(_9m*RMoxkzO3bRHW*jns2Z|xkA1@fA+rNF$_uczjRP5ndetVU-MOv$` z`UFM>=J%*p$~V}1On zC3`zAn+hwS0lBFqi3%0DIeEoa6}C!XbFF}Ekg&dz0$52&wyjcxZ-9bxeo?A|iJpm` zfv#&sW|@(a9hZVlQA(Oskc%7C2q4c^DWjyMz)D}gyu4hm+*mKaC|%#s($Z4jz)0W7 zNEfI=x41H|B(Xv_uUHvm1jG!N)Z*l#%z~24{5%DanTbjHr6smXNP z3=ITeaOi_%^bPe4^pTa9WTxRz4w6AA2Whqn$gD`siEzoxP0cF?I>A=S(8vO87(zA@ zN!H8+ED18m$}=}HJvBTtr6dEW3r*M~H8VW}=nbHHeNbrWLxT$#`ugzT2ZaIc!Kfu9 zh4E-`jRqGTqK16Ns32P*U$utUq8EKqtpj-^DjP|2ULIUp84hv*;z?pGpR!aK%+GE5bcqtFKbOWH&3+i!rr9 z=1kb-Lhf~%^Zi1)FPvt&Vsq$iLuCDqju%VLaP_kK%s)E6Bc`|HhxmDpBYbVzHEFu1 z^y?<*)*pN+r*Q7Y;*;CT1rJo?A4_lKu6*?T@Ypf6_cUv!Y)5 zKy9Sj8~4uH=fW=b@s+V{U2wl6{0}qBh4}?53jg+Rwbjhgp7i@S*Mh{P*jveUIbi_~ zkFMyx{3A9wC(!Ei+f&-DE59}c$-hsXXl3)(!DVN}?)~8z0lOn_u6M}QzEYp%xc%n6 z-N(;g2tVt>6m4^C=Tpt9Ccmw0A1}zPDg3=y+mKJ-y?w~?BR20p7zGwMo(y8>Vp5MN z4>tc}6so*oM+&R2oYaMYG|fp(H9vV(Sw8NN{IA5*UU5wC>g{*EMSoR8ooDuk%~$^u z^L*d&+Xo)b`dK3U%u;Es@STP3lfK8jdNYGZ`3u9w?N5!~YGnmy+?zTp{Xu;n_?o?bCe^KC4Rt~2zzdPHPd!IInRmZjVF9j(>&t2{8#g5O}{jvoalY+~cv zmD^_cv48(+J^fz6k@p7myx-?{EohTc^O|vR`DM)mNk67{%0}=Ch5k^|G#B~vE9|#v zG1tr5?(cKz($c*>chCJ+fBMIZfW5zG<>n|d2(R6~Y8H$3L9y@5-}sCF_Wj>2FHkF1 zSp93a;ic=xohn_c4o->BRGlVoAM>T9?s`bLUD&ZbhEwjTNCa^)6|Cf$v#I`H+RtCz zuQP*^v>VpEUU^tPGilq2S(nP*`EHmvX^HgqzWFnhCY`+Q`A+`eFLA$}S5E}7iU+cZ zXq9~bWv=V$lOJmvIBQP8UXDlV{2Lftf9%K&uiMbOFOoa!UgZ17cl2<5{8h(qQtz+Vg=9K#Pn2YAJaCV0)I~z z$B>MBZ_hLGGB9v3FUbCXZhLz(o6qO-ZeFAVE%r(G8SAxEHyZ+tX7F_Nb6Mw<&;$V7 C>o;ov literal 451 zcmV;!0X+VRP)M?s9>M``&~-il000McNliru-2?~@A}>_EeGLEr0Z>Uq zK~y-)t&%ZL!$1&4*K*+oVdxRLM%*M6T!A`g2u)-O;oN{43B@hq3N+i&;1eK+3m_*V zB$ga6e>~1=$4-O9uSQQVKeM}5>Yp+&O^UyO<$a)sr33WHm*C-Yn(bl-q>EUB@q3(= zkpNR2N#N_~QGg&T-vme`NEZN~Vvi2cqeMq5ah48nPy2$T4AwOFjc24a3Yw31JSlY& z7=3FyE|fa;&0H9vXS}s*gsS$WF|U0#u8>I;8hsZOH1nna%VFqj%D_1bKyfx;;~Jrk zof?1BYz+W5&JpUURI;Mk8nrUA!+1t^0I+d`O!y}onyrCSY2a_AVfQ!~SX~!;$ zU_-Mta6xR$5bD4cZfUlLz4b!}fas|4P;Ahn!l>|+Gn)I~$9`|}oWV9n`bN{y8pk_& t#uw6pADSCO^XD2g#%m|abkcOV`33v%2Zo%LoI?Nr002ovPDHLkV1j1%y88eC diff --git a/companion/src/images/library/00020.png b/companion/src/images/library/00020.png index 9f3c5d78e040bf7ea81c74d87f2edabced38ae62..802e9885a8d41bc2573134d0c875e5e07a120834 100644 GIT binary patch literal 209 zcmeAS@N?(olHy`uVBq!ia0vp^SAf`o14uBqJF!g!Qk(@Ik;M!Q+`=Ht$S`Y;1W=H@ z#M9T6{T`D94;$Owbqp3jA<+`oh!W@g+}zZ>5{8h(qQtz+Vg=9K#Pn2YAJaCV0)I~z z$B>MBZ_hLGGB9v3FUbCXZhLz(o6qO-ZeFAVE%r(G8SAxEHyZ+tX7F_Nb6Mw<&;$V7 C>o;ov literal 764 zcmVM?s9>M``&~-il000McNliru-3ko=EDv)a6A}Ob0*OgP zK~y-)b&^47(@+@4zcs~99Lp+#V=^=FGQ4aD4`aBcLSaWwpjxmjJ{y!2l#D zW{4Y^g-b+6K|TafFffuLloSI%#nQ<5s`B-^Y>bSyc>R9LLO{tA#y1h~NgaHER$z3F zc@>8n7QfJw@u)i$7?x#r-hbpq|3e}X7+tet2?L)b0>bQK$1@Ccu zM3vB3oR*!<~O3MQ&7Py-SIpJ5q3dn4D*4lSKxEP@4!dkp`1TauKoj%`met7A0WC%n*w%s`jB0*jRE&nsiZfyXHej$qRi{hRR zzQ&cqfu`Yi4V!rg8;Xojwntg50a~CuYB|4|^Y0d;vrr_u`&4%cMudig{NQDNpyBYe z4Yxrr^NI+qP@nzc{!MJP{2`$;wtE{1b)gUmkM0z(P&gWO4DIR?BfMi#ju!f#6rQ6s zA{xJ|G9$HNKZIBi$2l0aYs4ntN8%5Ic}UP>-jW(6;~XrSM?1ASVegW7m5AttLVopo utk?UOsE5LOZ_d99WN{XF zL>4nJa0`PlBg3pY5H=O_IpecT>5$^E_lxd3cd4maSX9I{q~Y!-eChC)_|2# zHlNtOx?cGZ!^#uk+TLgDwEoc?hwy~e+#6;yS)_R$b$ztvq=etGW}Q#MMehR3S1WvS zwTL}9!|cP!$KR&&Pt#t}UFYC5=}o=JJ^sy1LYtm!f7I~jqJvi0$={PimRLQn>|;K> z&&RCLR`=Ysy8gRJ$k9D1HV7KUGkyqwI>m8@}dqp{&Z|7^4S@O9&ev2rN zV)n(_9m*RMoxkzO3bRHW*jns2Z|xkA1@fA+rNF$_uczjRP5ndetVU-MOv$` z`UFM>=J%*p$~V}1On zC3`zAn+hwS0lBFqi3%0DIeEoa6}C!XbFF}Ekg&dz0$52&wyjcxZ-9bxeo?A|iJpm` zfv#&sW|@(a9hZVlQA(Oskc%7C2q4c^DWjyMz)D}gyu4hm+*mKaC|%#s($Z4jz)0W7 zNEfI=x41H|B(Xv_uUHvm1jG!N)Z*l#%z~24{5%DanTbjHr6smXNP z3=ITeaOi_%^bPe4^pTa9WTxRz4w6AA2Whqn$gD`siEzoxP0cF?I>A=S(8vO87(zA@ zN!H8+ED18m$}=}HJvBTtr6dEW3r*M~H8VW}=nbHHeNbrWLxT$#`ugzT2ZaIc!Kfu9 zh4E-`jRqGTqK16Ns32P*U$ut>KO}7kqRC@mZpZ=0L_t?=-SzGrNM*UP|ZagyS+O9P+ zJL1+~S3bV;qmQr(1E)hDivr_`i3}3I3dipSp7X1Z4gXuluWN6V89pQUa(zVN zY)ikhzg-!wsI5rfe}292$vKPE&)ah}tbX;Ido?3N@cZ^ec7}yBs$;JQG2FRnethYs zE7$Vo*lv4g^?6_X{rR(AotawfF52?;o}Pctqc5SC)Y^U@&GMYqq9Aj;dgiu$S#xiF z{p-sZbMpD@Y(a*mHQU>~885uqvCgUb-N!Gy`~En$>PuhyXT9UPyJBU-jzquZt){_O ztWAAyQaN}CXsNWjr&vLcvB*)bs^9b$;StuHj zZhwX~LAEz!rmgduv_r~!?HA~5o5akp(s**dbFKS!<2_Ogn~q;t#U>VWVn*wicLBeO zRtj&n^0>~DJ>kp*dG8JC2J0& z?6fA`BtKu2^*~I?3~hr#qbcEwkL@hgxwY20(>wdauIS@4ZuXhGJJ&`A=>JU3(744> zc}&OfdD&KzEw}n6KkJZx_h{PPdSBje8ctlv{{7D+w$~op5w$`urG+QcciFn2$Hxu_ zBufi1U6}t@_W!o+hp&4_Nv}Jry>zSQ%WXAVjxPN6Ag)()fArJ_AH54J54GgX(Q;nL zeroDVm2R$s8?w5-aoh>WG+1?TMuOLY&(4?Bow^vU4((RRh&plb_`KRboThfyclNtX zu<3Xy)FgVB+vrKNV9^Wn{eO6-_AlVQxv%e1b= zORHVd4pGhe6KY%x+Fli#o^E=6aE&Hs=7kvkG<%1~8Ol5IGTgPNMJ2SmXE?h(I9ap2 zyr$T6mafFBzNhmqU$|O!%ONaN=+Pw8%!!Kt2uK(fZ z#CXYipR0F7FWyQ|Hx&4B*J5M%u7n?v{qrK?zutCfyR_Te_gU&<2A9uI&j0ma!JFmx zg1Nr3<)+x;BeS2!Pn#?IGn|#vfoXy=qX$C~dbawX{)fq?HZk?tp8X#|T{2HsKbLh* G2~7a+5VJb~ literal 572 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`!2%>J?r;ABq?nSt-CY>|xA&jf59DzcctjR6 zFmMZlFeAgPITAoY_7YEDSN3~M5?s1`2Rk?~GB7Zn^>lFzskrra=Iy>i20SjttN;Di zKX11t%;~7#F;9&UpZN?IZ&}L4Pio4Eul>6vje#uz8w%L{A?*7{PObyJ)Awt#7TkWi zz3r>hV6#lp8uGNvtZhgMD_(Ae}$4BO?84M)L%bs*();jKzm;EiF!tSBd zWp|0mKXAo4j_0lJ0u~!qt$ntlBeJ_jj@vK1LF3r@R}PF!i}eD|R=D!^8>LzPlR1>C zRh(Pkb?d>+Sf7=RN1H?EhKb~xSzJd4b?PY7u&U@>~HRt=?&u2RxwMlvk_ukG<^Rzdf z@SVvc`H+g<#pM&7Z%)3Y(xN+CvE-=9tDQW{%lNK{-EI7`vTOcrewV7f(-T$CKmW4B zBPqcD%95&wodN61icjynTP%IImT4#J0gpMmbqxOgW8~VA_ImgIo6&ovs$JLo$-BV7 ga{vc=uzOv6^Ys0R@7tHJ2F5jmr>mdKI;Vst07#AScmMzZ diff --git a/companion/src/images/library/00052.png b/companion/src/images/library/00052.png new file mode 100644 index 0000000000000000000000000000000000000000..64eca2f6622431d42cc2fe98cc671ec54334e97b GIT binary patch literal 3469 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`!2~2@x4h5*Qf*Zs5hX#1CLR`=Ysy8gRJ$k9D1HV7KUGkyqwI>m8@}dqp{&Z|7^4S@O9&ev2rN zV)n(_9m*RMoxkzO3bRHW*jns2Z|xkA1@fA+rNF$_uczjRP5ndetVU-MOv$` z`UFM>=J%*p$~V}1On zC3`zAn+hwS0lBFqi3%0DIeEoa6}C!XbFF}Ekg&dz0$52&wyjcxZ-9bxeo?A|iJpm` zfv#&sW|@(a9hZVlQA(Oskc%7C2q4c^DWjyMz)D}gyu4hm+*mKaC|%#s($Z4jz)0W7 zNEfI=x41H|B(Xv_uUHvm1jG!N)Z*l#%z~24{5%DanTbjHr6smXNP z3=ITeaOi_%^bPe4^pTa9WTxRz4w6AA2Whqn$gD`siEzoxP0cF?I>A=S(8vO87(zA@ zN!H8+ED18m$}=}HJvBTtr6dEW3r*M~H8VW}=nbHHeNbrWLxT$#`ugzT2ZaIc!Kfu9 zh4E-`jRqGTqK16Ns32P*U$(!%{4%=Ohe9m%cXFEE{NwI@_$E&K--4*9s zRxL1MGoKmfqi1$?Y2>xpA4?y}MsAH;duUfw?+2OOgI@XuEuD{wxmO?#~Z5CC-UzwmK!ps??>sbwl>aEW4!)Yp2?VUc7Yc z6NkL{Evwr8dgW(R|2eJR$PqdBb2#6+m@bxulNyY2?xwC#(%o|Jwm64a{_mIEl||e3 zNKaW9ohhdx7@F@Kw_HR0msCNOapkWzZKsPlr-azIyQugw-<+hhYVAyK8IOky>~?D( zF0DS_`a56i(BIz8Uf&d+exG>Q!aLf)@sCEq{fEL^-f;ImPCD>};ndkMUJjw0bI%#G z!khY1U5bi1_8Ri#wU*y_dQ?bYiTl!`&GC)iQ(p?P+ed0dZ8c_$i@s-+D(sl=vVXsW z3df(|fcV*Lu2(k*xm;$JV`bVmakNrEbpqyAOD_jerbdfXXdH0f8LW> zk1vcnzQ_56vfc4&X2w@x-XZ*QjsH$bCCuFV(Es*-e(_HqQ*J-W-r&AW;a29KbXk=K hmJ7(q&+O(u20lU0^PNAp%mk)u22WQ%mvv4FO#qlUGS2`2 literal 0 HcmV?d00001 diff --git a/companion/src/images/library/00053.png b/companion/src/images/library/00053.png new file mode 100644 index 0000000000000000000000000000000000000000..c73a997018e588451bdf45c8c1d740f5ab917342 GIT binary patch literal 425 zcmV;a0apHrP)Rr00AjUL_t(I%gxfiYlA=(2k;jJZxLQchc1QEIo&b{`BxlDx&*3wX)O*e zg0oBeuUHC^g5cV2_6K!M=}-f~i}x;8y(L2%=)*xi+}->7Jb--^_Wf=ToJemR1N`PyJcCO|3E3fmfHFa zP}>G57)N9jOw2<>Un6QF`gTm7dI$ah_EJgz&vh`Wn-{&ma4g_DkE}%=+=riWaT+!- zn`g5{mL<<|?2VtcFmJ)>flB}qCN0pGi_n^6X<{!|o;Vc1kV(3GWypaf@V{#V0J_Pe T@aYwq00000NkvXXu0mjfRS&14 literal 0 HcmV?d00001 diff --git a/companion/src/images/library/00054.png b/companion/src/images/library/00054.png new file mode 100644 index 0000000000000000000000000000000000000000..e4d1878c923b1146164338789ae4317529cc06ed GIT binary patch literal 341 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`$P6T3NW8THQfvV}A+G=b{|7Qd4_&SUQjAI7 z?k)@+tg;?J4rhT!WHAE+w=f7ZGR&GI0Tg5}@$_|Nzsn*c%xbw&v+EL2=&GlSV~EA+ zx0ejL4jG8BJ#bhUDI;Ue;VRI-FkJHmV^oZ5u+^UEifPmMj;;*PSowz9*@O1TaS?83{1OU-+e%b&4 literal 0 HcmV?d00001 diff --git a/companion/src/images/library/00055.png b/companion/src/images/library/00055.png new file mode 100644 index 0000000000000000000000000000000000000000..5bf13ecb2db9a290b2c6562947003a438e6da7c5 GIT binary patch literal 325 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`$P6T3NW8THQfvV}A+G=b{|7Qd4_&SUQk(@I zk;M!Q+`=Ht$S`Y;1W=H@#M9T6{Vt2NIG4)#%&dh#p-Y}Fjv*GOw_ZNTd00V&E#ax` z8^t5p{H<#)Ffy&X!pQXTnrM|*c%g{O0WE zv&N<=$&>M@o@=sA^P>Xgmv#32N`@y&+DyK3K8RCmnEm_o9-013yPLnivRO&keLGgO RtqbTo22WQ%mvv4FO#ovxdFKEC literal 0 HcmV?d00001 diff --git a/companion/src/images/library/00056.png b/companion/src/images/library/00056.png new file mode 100644 index 0000000000000000000000000000000000000000..c44d1a5e0f48e0b4efa0f69bc07065c5dd77fecc GIT binary patch literal 603 zcmV-h0;K(kP)~fWyrUZcb(y|_qmds8T<0^AI5jSjrUKo3+<<%3;p3X z&Gp*wH{6=>RYX+s5k^UQpl5|1w50@XuX3t1`aqF_00004001BW0003100;m8Kmf4m pLglRgkNBy$~r0002AM!zfkLA7SEnu-7b002ovPDHLkV1ndf1^EB~ literal 0 HcmV?d00001 diff --git a/companion/src/images/library/00057.png b/companion/src/images/library/00057.png new file mode 100644 index 0000000000000000000000000000000000000000..678355ae01046bc6cbffeb5154ee2650c372f43d GIT binary patch literal 634 zcmV-=0)_pFP)|ghCdPFCGFgbg>Lc(dN2fR7u@u($Og1kDT= zovtbZru$vw_GThr?df*nTOttL+sSuJ1cHv8tSk|5xxb&>^equENPmrc&n*!kIRGlq z02%`<@S>{@CQsEUvBzN>xg%rxKtXX3J-)ITxb0E5ejNHAU_T_ zu5aY^8b`=32CgzxvkwehKmgFi0)fH+z{(6i;YF-ikHW;WY@?f=aar%O|GP)&>F*Jg zUjQ_co_G-AjF-L@QV^VZFkkMX Uh5FI?1poj507*qoM6N<$f|Gd{F#rGn literal 0 HcmV?d00001 diff --git a/companion/src/images/library/00058.png b/companion/src/images/library/00058.png new file mode 100644 index 0000000000000000000000000000000000000000..fa384d1e69d6717e7dc37c1f73537364befb0c16 GIT binary patch literal 3760 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`!2~2@x4h5*Qf*Zs5hX#1CLR`=Ysy8gRJ$k9D1HV7KUGkyqwI>m8@}dqp{&Z|7^4S@O9&ev2rN zV)n(_9m*RMoxkzO3bRHW*jns2Z|xkA1@fA+rNF$_uczjRP5ndetVU-MOv$` z`UFM>=J%*p$~V}1On zC3`zAn+hwS0lBFqi3%0DIeEoa6}C!XbFF}Ekg&dz0$52&wyjcxZ-9bxeo?A|iJpm` zfv#&sW|@(a9hZVlQA(Oskc%7C2q4c^DWjyMz)D}gyu4hm+*mKaC|%#s($Z4jz)0W7 zNEfI=x41H|B(Xv_uUHvm1jG!N)Z*l#%z~24{5%DanTbjHr6smXNP z3=ITeaOi_%^bPe4^pTa9WTxRz4w6AA2Whqn$gD`siEzoxP0cF?I>A=S(8vO87(zA@ zN!H8+ED18m$}=}HJvBTtr6dEW3r*M~H8VW}=nbHHeNbrWLxT$#`ugzT2ZaIc!Kfu9 zh4E-`jRqGTqK16Ns32P*U$utUq8EKqtpj-^DjP|2ULIUp84hv*;z?pGpR!aK%+GE5bcqtFKbOWH&3+i!rr9 z=1kb-Lhf~%^Zi1)FPvt&Vsq$iLuCDqju%VLaP_kK%s)E6Bc`|HhxmDpBYbVzHEFu1 z^y?<*)*pN+r*Q7Y;*;CT1rJo?A4_lKu6*?T@Ypf6_cUv!Y)5 zKy9Sj8~4uH=fW=b@s+V{U2wl6{0}qBh4}?53jg+Rwbjhgp7i@S*Mh{P*jveUIbi_~ zkFMyx{3A9wC(!Ei+f&-DE59}c$-hsXXl3)(!DVN}?)~8z0lOn_u6M}QzEYp%xc%n6 z-N(;g2tVt>6m4^C=Tpt9Ccmw0A1}zPDg3=y+mKJ-y?w~?BR20p7zGwMo(y8>Vp5MN z4>tc}6so*oM+&R2oYaMYG|fp(H9vV(Sw8NN{IA5*UU5wC>g{*EMSoR8ooDuk%~$^u z^L*d&+Xo)b`dK3U%u;Es@STP3lfK8jdNYGZ`3u9w?N5!~YGnmy+?zTp{Xu;n_?o?bCe^KC4Rt~2zzdPHPd!IInRmZjVF9j(>&t2{8#g5O}{jvoalY+~cv zmD^_cv48(+J^fz6k@p7myx-?{EohTc^O|vR`DM)mNk67{%0}=Ch5k^|G#B~vE9|#v zG1tr5?(cKz($c*>chCJ+fBMIZfW5zG<>n|d2(R6~Y8H$3L9y@5-}sCF_Wj>2FHkF1 zSp93a;ic=xohn_c4o->BRGlVoAM>T9?s`bLUD&ZbhEwjTNCa^)6|Cf$v#I`H+RtCz zuQP*^v>VpEUU^tPGilq2S(nP*`EHmvX^HgqzWFnhCY`+Q`A+`eFLA$}S5E}7iU+cZ zXq9~bWv=V$lOJmvIBQP8UXDlV{2Lftf9%K&uiMbOFOoa!UgZ17cl2<M?s9>M``&~-il000McNliru-2?~@A}>_EeGLEr0Z>Uq zK~y-)t&%ZL!$1&4*K*+oVdxRLM%*M6T!A`g2u)-O;oN{43B@hq3N+i&;1eK+3m_*V zB$ga6e>~1=$4-O9uSQQVKeM}5>Yp+&O^UyO<$a)sr33WHm*C-Yn(bl-q>EUB@q3(= zkpNR2N#N_~QGg&T-vme`NEZN~Vvi2cqeMq5ah48nPy2$T4AwOFjc24a3Yw31JSlY& z7=3FyE|fa;&0H9vXS}s*gsS$WF|U0#u8>I;8hsZOH1nna%VFqj%D_1bKyfx;;~Jrk zof?1BYz+W5&JpUURI;Mk8nrUA!+1t^0I+d`O!y}onyrCSY2a_AVfQ!~SX~!;$ zU_-Mta6xR$5bD4cZfUlLz4b!}fas|4P;Ahn!l>|+Gn)I~$9`|}oWV9n`bN{y8pk_& t#uw6pADSCO^XD2g#%m|abkcOV`33v%2Zo%LoI?Nr002ovPDHLkV1j1%y88eC literal 0 HcmV?d00001 diff --git a/companion/src/images/library/00060.png b/companion/src/images/library/00060.png new file mode 100644 index 0000000000000000000000000000000000000000..9f3c5d78e040bf7ea81c74d87f2edabced38ae62 GIT binary patch literal 764 zcmVM?s9>M``&~-il000McNliru-3ko=EDv)a6A}Ob0*OgP zK~y-)b&^47(@+@4zcs~99Lp+#V=^=FGQ4aD4`aBcLSaWwpjxmjJ{y!2l#D zW{4Y^g-b+6K|TafFffuLloSI%#nQ<5s`B-^Y>bSyc>R9LLO{tA#y1h~NgaHER$z3F zc@>8n7QfJw@u)i$7?x#r-hbpq|3e}X7+tet2?L)b0>bQK$1@Ccu zM3vB3oR*!<~O3MQ&7Py-SIpJ5q3dn4D*4lSKxEP@4!dkp`1TauKoj%`met7A0WC%n*w%s`jB0*jRE&nsiZfyXHej$qRi{hRR zzQ&cqfu`Yi4V!rg8;Xojwntg50a~CuYB|4|^Y0d;vrr_u`&4%cMudig{NQDNpyBYe z4Yxrr^NI+qP@nzc{!MJP{2`$;wtE{1b)gUmkM0z(P&gWO4DIR?BfMi#ju!f#6rQ6s zA{xJ|G9$HNKZIBi$2l0aYs4ntN8%5Ic}UP>-jW(6;~XrSM?1ASVegW7m5AttLVopo utk?UOsE5LOo}TJs$;;9*M$m$mxF_C%>8 zMmzYdr-k@n~ z^pI(d_X)NMl~NfeR-TrS>RFN_7t+@3Aa^C~|2p+tt&N*)j9aFF{OalI=d#Wzp$Pz} CDStKq literal 0 HcmV?d00001 diff --git a/companion/src/images/library/10702.png b/companion/src/images/library/10702.png index 5c05c20a69eedf9e08c5d70398dc25ea154169c0..c1f70cd82e1bf50e86d14a7bbaa39cb1dcf05f10 100644 GIT binary patch literal 572 zcmeAS@N?(olHy`uVBq!ia0vp^4M6O`!2%>J?r;ABq?nSt-CY>|xA&jf59DzcctjR6 zFmMZlFeAgPITAoY_7YEDSN3~M5?s1`2Rk?~GB7Zn^>lFzskrra=Iy>i20SjttN;Di zKX11t%;~7#F;9&UpZN?IZ&}L4Pio4Eul>6vje#uz8w%L{A?*7{PObyJ)Awt#7TkWi zz3r>hV6#lp8uGNvtZhgMD_(Ae}$4BO?84M)L%bs*();jKzm;EiF!tSBd zWp|0mKXAo4j_0lJ0u~!qt$ntlBeJ_jj@vK1LF3r@R}PF!i}eD|R=D!^8>LzPlR1>C zRh(Pkb?d>+Sf7=RN1H?EhKb~xSzJd4b?PY7u&U@>~HRt=?&u2RxwMlvk_ukG<^Rzdf z@SVvc`H+g<#pM&7Z%)3Y(xN+CvE-=9tDQW{%lNK{-EI7`vTOcrewV7f(-T$CKmW4B zBPqcD%95&wodN61icjynTP%IImT4#J0gpMmbqxOgW8~VA_ImgIo6&ovs$JLo$-BV7 ga{vc=uzOv6^Ys0R@7tHJ2F5jmr>mdKI;Vst07#AScmMzZ delta 359 zcmdnP@{MVNL_H%j0|UbgiMKXDiY>q=#P$FG|3GHwq04nZiZRLC-G!lpRn`N@;Vkfo zEM{QfRt90l+soFv0R`DhJbhi+?=eX+afvvY-u?>|5-o9!C~?lu%}vcKVQ@?-%1q2t zaLi3gElTgt^f&-iaMjbrF~s8Z+l$tG^@j|2*b?03jGl4WdaXZtrQL$T{ejj>BZDI5 zf}^arbUgxlCx_$;a(ncA6{&T8bD!+41)_E~jRPZ>{bXyCVC_^{=W%7Pi;D@+*M zHqBIZ(3D@K|AtK`BkC55#<|{xdk6M1CYPSqwYK7r$V|}byR%tZ=>`7`BO5m-c}8cp zUkO}?e#_VF$#vY7a^piYD#qZUqkvguG+ zqt|iO%}Phtbx+t9=g+;Op=kOc^$miT7JmCxzL#Oq+dXwxGK4LGUS#le^>bP0l+XkK DQ=^Hs From 3f03abc0d1b34753543b80a74e007b4a7ce55280 Mon Sep 17 00:00:00 2001 From: bsongis Date: Wed, 26 Feb 2014 12:02:24 +0100 Subject: [PATCH 77/89] EEPROM conversion bug with telemetry values in logical switches --- .../src/firmwares/opentx/opentxeeprom.cpp | 43 +++++++++++++++++++ 1 file changed, 43 insertions(+) diff --git a/companion/src/firmwares/opentx/opentxeeprom.cpp b/companion/src/firmwares/opentx/opentxeeprom.cpp index de08d6abb..8090aaf33 100644 --- a/companion/src/firmwares/opentx/opentxeeprom.cpp +++ b/companion/src/firmwares/opentx/opentxeeprom.cpp @@ -1263,6 +1263,49 @@ class LogicalSwitchField: public TransformedField { else if (csw.func != LS_FN_OFF) { sourcesConversionTable->importValue((uint8_t)v1, csw.val1); csw.val2 = v2; + RawSource val1(csw.val1); + if (IS_ARM(board) && version < 216 && val1.type == SOURCE_TYPE_TELEMETRY) { + switch (val1.index) { + case TELEMETRY_SOURCE_TIMER1: + case TELEMETRY_SOURCE_TIMER2: + csw.val2 = (csw.val2 + 128) * 3; + break; + case TELEMETRY_SOURCE_ALT: + case TELEMETRY_SOURCE_GPS_ALT: + case TELEMETRY_SOURCE_ALT_MIN: + case TELEMETRY_SOURCE_ALT_MAX: + csw.val2 = (csw.val2 + 128) * 8 - 500; + break; + case TELEMETRY_SOURCE_RPM: + case TELEMETRY_SOURCE_RPM_MAX: + csw.val2 = (csw.val2 + 128) * 50; + break; + case TELEMETRY_SOURCE_T1: + case TELEMETRY_SOURCE_T2: + case TELEMETRY_SOURCE_T1_MAX: + case TELEMETRY_SOURCE_T2_MAX: + csw.val2 = (csw.val2 + 128) + 30; + break; + case TELEMETRY_SOURCE_CELL: + case TELEMETRY_SOURCE_HDG: + csw.val2 = (csw.val2 + 128) * 2; + break; + case TELEMETRY_SOURCE_DIST: + case TELEMETRY_SOURCE_DIST_MAX: + csw.val2 = (csw.val2 + 128) * 8; + break; + case TELEMETRY_SOURCE_CURRENT: + case TELEMETRY_SOURCE_POWER: + csw.val2 = (csw.val2 + 128) * 5; + break; + case TELEMETRY_SOURCE_CONSUMPTION: + csw.val2 = (csw.val2 + 128) * 20; + break; + default: + csw.val2 += 128; + break; + } + } } } From 356980fac3525df45d831fad857fa16b68c543f4 Mon Sep 17 00:00:00 2001 From: Kjell Kernen Date: Wed, 26 Feb 2014 14:41:06 +0100 Subject: [PATCH 78/89] Two new splash screens. --- companion/src/images/library/00007.png | Bin 1343 -> 3439 bytes companion/src/images/library/00008.png | Bin 209 -> 1343 bytes companion/src/images/library/00009.png | Bin 209 -> 27584 bytes 3 files changed, 0 insertions(+), 0 deletions(-) diff --git a/companion/src/images/library/00007.png b/companion/src/images/library/00007.png index 14b5b77445e9242a3535546e488a6f1d5776d007..358a29faf33932e53bf71fdae1c402843152dc20 100644 GIT binary patch delta 3418 zcmZ`+c{tSV*B|>}vSlr)5h6+1#+0oY`xc@?vKvdbXNZWetYgj2V~c2LY>AXH43(V* zlPqJ%K4dJ}%95Ywd9UC5{`KD1bar_X~Ok zCT1>IUD-e&2-!gUmSyk+-7d_}azsFLo$j_}!Z^x$FCV6Kq{UXGL)GqcK5UFLUAjb*=mViQs*q%(hsOvNnSIrWkI;g%2FK8ccFjRLE>{4`4lV( zo78Xo)~34bGDq4=;RO!!xX}cXvJ8hz>nY|32O~Q)Qp!2sxN3mr0}orV^{bilob8@@ zzCkM`#*TREsP0QkD#a%ze-gHalC2 zhVLs!rZG4}@M}^HJdE;$4WZ9nT?QSk9O=2K5y`c!95srxtEVD4Pt^C>1kA;L zDhpItnEVDCJn~LQTKr>AhSgw$Ah^8^p12w!!TjK=P=H+=)&s=6B0uW5*l%wj`Mh|3 zAOsw_Jg6+hJoi1R^wn!%{DpDa1%B0ll2RS7&gJ7mZR4b!iHnwoh8(J+Lz9zWsA_bV zVZ6_qyZ4F&CU@DPZNf}TlUu-^1EZFQN4(`OxO4%ESQcTAi~XcF2-_S zN*vG?w36(E1J+jrBYDDSf7E#;^0w}rQh35@-!R9!jgR3!&pn$8MbZ-GTT}DSv#w6O zON`|@xAMc!>(xO*kO==ZwN?c9y$^G6gbA`q{BC8Iu(L~YJhUBd?Np`YIQ#ichK#s> z#c3-mB~{tPm6a6?27?xR`ix;BJ7QljF@|~Rvk2!t0dO$N#Z{E0=0_Bu@td7zmzO1t zZcuBr?menl7{YvH;dGy9@aSYLXEs;rK#hL4(`VQ#@XT|&|2p;D$ObRz2!|VPLN9gu zoHu0S5=-b7jt=Y-!i;m1us7EUQGfjv%Zr*kw#~i%W2(p8ijOBVD@%uojjOC-8}eyi zI$;>62SgHHd>S+Ld;ZS&#|zzenqOm$u^&FDo`Ly@hHbR7Rri(~|BdKMIaivOm-nT* zv82KROuEM(bNTXRX&5XAG&u3j>vcs%x3q0bh_al0YXJtsC90~GA!V{MwjatPB&3)8 zMOVC|C9vM6I-Fe0{1nw;OB=@lMp95a| z`!&Cr{18vo#PZ;$DUCkp(7=G$#ZIYfB!>H7hP62^UW67|$*=RxT89wQM_xrmFe@vI zE*32-D?3zcPkghd&L6zK8Osm4aN^RAE-Nc54jkxxTb_e=Rufyt)spp5kfiHMFc=aT zRRS*-#haXkISzl0H?vaC6IB>murt)xZ(GT#1cCC5qAEKUq_TX2NpnYYNuQoHLFZK% zdjjUWd6A3;0?U8$p*jWz@#f`KRS@myw{I2Z>eJKtq!aion!AoeMe*2A3x7RBujxtq z3M0`T5uofV;T&};whbYwrDSi)B{(2rYdEdMxbSSs8p<4vn$=4YcHD2uxO98>&cy7j z6Y=N2swd;pdk+Ilx7lP$m0{@KubK_FYGa4R`f)-O9XQRNBzyNz#wl7{e13jjn9}L6aLzh2Iy(C5X+!hOyJfv368Doz zJ?&h@CD__lMi)ZFR&9U<^+~d0!A zdFcq-_m4_CvAQ_5pO>nW)NM+B&IdlM)o99LEjHma`LVs4j4X zuZ8rZ-339wQk$ka+m^m{MSB$6dykR=({gD0mCU{cg(`!4S1d!9@Mf+Z2?A@Y;$Pa; zDH@>emYXp5qmL{x)S~9)4}K4eN-$vO&Pl%P!|J`>zNp5%pZJ^z5P}|FOQ3*XNgKW| zEQypM2IYSn9E`x@@us|n=KPsCIc(nb1cKT;`~iRu5K$Ep^UuIFlqtDW1LX?p~>$3 z@5O<9WFGP3$C$xDt}ii;h2fbQWZYEVNQdL!OEH|BuX5zg8oeok+3gPr?*5gHhDL_T zAV6Y?QAY<*dSOx}T~SrFO~Ez_#O)t$ktmYJ*En4oCxuG*dXEefL(O~o`l4P+clY%v zu6aFr1o2pNBYk0W7BwahO@2+ft?{SKs&I3zGsZRC$jImwg&;THght(GRlk0HsJ4*J zP3^n?x&rNnp5x3%Qx$JK;-6ZAiy8TF&UC4nTf*%?~bEvtuNKCj@Nfd_nrJx z*zPwSMoxkVfWOx@p>0Q+9@tNNqgVWXBC`@+F^1OtuaL_;llzp$Xk6VuNr8-C@$tQl55E&-_+9 zL6*Jl+yyxN?~{!2FU-u5qSXudTv(R7cO1$C*disaMUc*ko?gV5(OmVue zKd`x{u1*C{|8{-b-&L|nX`mLUT0E%FggZDiZ_U%mGtV{3s%_u%owO?50)MBZG>3wK z&WgsyY>gXFbCvAY>#X-i*QRCljkUs#B=1yCWXrv}ATGn3ttZw4^DZoUI?JuFL-RD! z)x|HfH+%P2Tl8F%7EDa&%lTn4Fc5q1Ti=7$B5~WPr}cKS3vyoW?phXrMf%AM(WBWr zr5xn*v*)DrR~XXM(}!oulwr!Zz|Zjb8`}n^*&OG0uXPKOZ^psVi~5KiCF^>(WDogt z^0M}~;#(G*pBe@zEulHTGof+F*4ClZ9iH!I`$f=Co=x4jE&s$Yz4)x_>KJ8c&<|dA z-{SG(MhVN?S^fR}sZmh?id582T0bMtK9rRMKaeP0r3N8VxN9CXS+qKgkzJ<<(}9Cy&;+aoz`F}XIhFGnvUgPn3!({UEB9QNkH80g2GJ#R&g;JFT zHny4LiJGCYZ|mt2Jb^epa|3Ddm#1p0$|Ij_H4AR;nrEBwUz!-S3uDs~y858F1WEro zJe$y4_m*eq#mhS9;lZNBry{vR!DKx zE$hq)SeC`XE`4X|svWs|=7au8LC*WB(#RwY<=>PC>1KR%Y+ZDD6+8%#BZ000E9Nklas4n6y2yPZ50#|u^N96p@kAt`?FBA8x>TF;6gWou2q_iKZvWM zSY5agQAkv1+T?V9k-Y1jbLZYWbMH-F?wfP6$USGy_vTDa=I5Ka^Ar)F01%oY+LY9Y z)c7Ms#db|apgd2(RgcqSd20f*G&p+-u6kSpIigTZ1XnFCH&ImZg9TSDj?GbN<0e4S z+owZk zGOZQ&I5ioQoN}Hj+XFWy{UDE@egHr>h7%=UvoySeCkdb5QdS$fflUY4fo_|-ZixyPxM_a>t+lbOo6 zD&z`Ius*gK+YQSQzQSl~e|BqMw1uQB+nXV1Wrsch=)`S&9McCe%P8N1leSsMD^4xU zsl2>@#zy=X)6Fzpwxr2FPR~Sz&79KZre&X^IfreoBu+N;h4=Q{9K0w!^Z~$IxQ3M$ z`&wK~9bSFn)S)paj(ahI`xL;rlr;IrnaQIW`+od?lv0OZoWi3jNz@G7#!_p^zgU4gsfntP zM+tLsk>f_1UdNt0@CV+lpoZK;33JMq4d^lSKI3@s6Z}#|B@`X!6H)ANpAvf9CtlVb zI3&v6NcKwab=|spBefi{087D`V4CqPFV+Qk2vF;)?9lfGjWXZ$<0aGR zAuHKxslz>LxgS+xdESM)=rSxfuqt|9hYM_veL4QJ?)ACFX-sM1X~lb#qN~hrl)4R% z>#Y1Hb)+sP@-!VDbE=AQ?Zz5rIfGk&hW;Jvo8760Aue%RGf9bsqnlPgT+tr&DGf8P zA^ITUb(Z;z&}y$96{|m7=2Rw8GwFW9>!8JNA-!T=k7#zGIOTp+AvuAMnB}qMJtN== zdr1sf9D5Z;?ngP}69_S zXLxxLP_!ErREpq2H-fHJnvFk*tD;z4xDioERA}1dbdkL4opa~jJ9F<%UhbQ7vdBGW z&iCd_PUh#Ex$_hepa2k>BHEPHh}8IhBSpn_O+}zQPr+4>(_?vS0<$zYdkU_4Tmw0x zP)r0@EiN}vRPciZS1pdsQEB5QK+)u;n6Ka_1E-shWX(He{2vHzGI5HCkDx_5r{E?U zr^n1@msAGCO%vP%GDx<5ZxKnT%?2lHA*;LuWFr756wb8IzoHo+{e|HzxfckDq=3KsSaHC10~N zyn`nRpWjoK7kTZ|p);AHatl8sY=_Wc=-aS>c|5=#HrTnwsmlxo?T*Wqe*DQSOYm(> zn~wdgd;~psRWMH7%pDb&s@olZmn|dMgqO^A5YwXP9hlEbk6@s1oSMcnY0D->StcXr z6f3Jcu8cgyPG(tzt>aI#(96p1;`@|7uFf3OL|nG5yo z_ObJ*_GeBmJc>Nn)_b^z_YKQF9Kjs?joF5EFMj5Kdaw3rcSb@5natFG#+8+4_=Z_} z(TQG`rtA3CIwQHqsg?I8qc4-0%D5`z3Qn*-wi(+E%MiZ8Xlj3UYhSd5q%7N;A!ucX zJ^<*%ZG0Tl2QkYi--462S;s3*EzGIByv9cS7t_r&UACmjKTgj?h0UDO<)&qyqB)0c zt|U%2^o95K+#I|pJ@f&8z+1S6l@|M2TudEaed5%iF(;0DF@gIOz`2w(`Nx^bqe6Il zu8PG()9V^OXSQXy=U7KxoH;zI-OsA3lwFB50mpI{0Uqs>`%%^OsO1>I+ZOwN{FG9M zU!20DDoNA~+{RLC$-h{EJE@7PkVgq~a*^XknqJ4AJMahIt)PZ~+(Zd;%9jo3G4wv; zc<>YaQbi>c9p@8K>~NnFdfX>o)*d({%HBx!OB5f{py544bLlAigfA_1_{ACc{iyQN zf%BMYSPtVke#D?*JB4`;V?tK@qN8|o5aB~g+)gog{c&Zb51$$OBm4&7Df$d+7fx9R zYmYeNosTFqt?bZ$_XUkI-}U1q)94{9*=ni7J!-ihRbqMGg}dl7EH|(!dR~VMY>$08 z{<7}%xy5NrY2j(bdz7N9%x{#s4Ug-r{3dmzE++Cc9UgP4igE468fH0zTZaA}>zm!F zhaoO;S~E$Bg`=BRKU~os^(hTAuOa#%;dPezjL>SY9u=#9KV0TiCQ&o#e!}aZ#cv_K zVqTAEcA+@sepDejfsdHwvE@A@;0b$43|Jg{6-MqyIpgGhl-!T!n^KM?G11}j#!C!81Rz0P(rEC4}?M!Un%iWLQ zuh_2YopV;OyLRoetuy{eL80Jy`J(e>b57T*&X$}fRZnS~3t!$sLBUC(swk)D_VaIv ztK0p{i*qZnj|6KqB2~wu56P?iKKzzK=!}lsdAZK(nZMt7p7SZXx3k{QQ2YJ$Q9s6= z=|WpoMAqNbYgSR=JsunR$y|JNp`yRk`00rLoOfdX@q`hMhmlLAV;S*73oAa2PUa@Q zE4kVE`78xScjc4b_fJyv%z8|ElswlHV%)lEN8pA4d9Kp_NwEX1>-JNR?)?lHK)*>b)6;waC{zS&Nr{Ao0v9eYUO((Ss+ZPx~ z#cSgAZ1dtie2~)<+Uf1>&9ZHChpi-DB)c`Vap;o0eRxU=59^LCnVFftXFVQk@~frl z&gdjJJ<-p2-9Fm4i*3ginM9fZ`J1}wio!7m@kX7tHI|3^rWYt!SXgKqGj!7{y;CJb zML8EU^fQ!9t{-JvU0rpPX5YMd^B1e!hYc2ZO*%R{d=hE)#&8E$DOSr|19S0Mw;eI{ zywxYOTQ~H$6zODqvplpL9|K=KO!-z#Kix`H{a|0AV}a3~ID^dUk=gY<(+lCX=JQ@M zlX>{&dF>7F-&1V9weCh~sf+{L)z2^W_bDew+`PFC-`B^-=WT9o@A&w=))6JXsL7RI z(+i5-`~4&v#OeR zD>26NJ%0SS*>?Zix1Z_>y*9`+D-mpbd_+M=Nj z;O6G8yd4}C#(U(*u8ePL3JM#Plj$<`)vc}fZP>73apOq1l>CwFIsVZiZiBAU`!=t0C+H$VEKDVEIx*tDOe0*ebb929b z|4z@r(b!uNSX*D8{N%|E^%&u%=H~LR>8I1PvVKKr$@Hei7?%$_Pu0k-MhKpM_NAla zQvfxy+hFwBeCJ_$e$B_GgLTnZi^=8b#(tL~_pySZk9Bo@zAM>lRW~EoZ&s;+T^t`7=vSg1#{~SV9uZYZit2G&Guc{hkq+7D?85qIn&qI_hr~w z@64Irp`nvDHZP?HGG4r(pxnNFC-ss2`?tl^D`8!6L^p2Q)YRRrWn{!k&9vXNHR}R4 z;h#T$D%WxB*`x03D~m^f4ZeQ;`Y$81_z-lvb_I9Zre$Z-lo)HBKFxr~_4t_Uj#S-X zM>)8;Cdd^YddlXtB*8lL@b=qCzPY z9rFJDiK9o4er#;48Fir^X=`b@^}&==RyGlPwB_f|x(XUujqBGBU#h;tB_qR*O^?NI zXlOufn3|eWQBx})nijkMN6+V9PNKu=vU~NNT@??-E=|nMr4w2saP{E{fkwy)p5O?G*X)3LH@T)isj z?(VLUC=*Y`z-M2>=1RL~PkmJ=vx5}t9kyc+Vh>)SXJFX-@_}Yr#mMYby~%2%?Ak)3 z^y+;7+q}F`1+Ie!8Blhs%zFE(LhtN4c>8M0GcnJ9HqTDQDW5yX!r?Q|wKO+=r8z~F z{EGSI%dcI>jq!@R4qGwelg-S{wRCmeRZD$ZR228?mxY?TdaSIk%*nf~bd81Pwe<4x z^3O9fFMoO{w*NxmeH`<5cHN&NdDR~tapJ=!FJAnUfx2+ewnIueY_}3h4O8f*0wYaR zQ%>>NI~OZ%i($R7sfD7qVuRp;OG!O^eW_-vde5XAIcvee!Dvs|;Pz6i+ji^__nNoI zMx)%et+KnD1B!J@+Q&>Pba>un2%`OxH0!9P7ZOdY1IU~J5ul$0cZ z(>(Jxki#eFgQ+Rj69v)0(6GQ`RtWouap%s6M~^}h6FK;`5_m*K!%;VP@7_(hV+Wsz z2u*ft{a}4edU|?Na`LUh!lSooIPO-N$)&X<>1PB71@%<#u`|a(nqOLCpr_~VAWsCx zi;Ig3&kEhZ(#A$HRrg|Edw@C}6VvS`OGUn@i=r%e2I!<%8!EgDC+7{+NCrkmMU;5d zO`}pTa-#S&9=`vUaaM5Oz73pwe7D2HY4N-)EiIqmz`c4UdYA23HOJcgNsGpWQ~13Y z;S1#!IT5k3!T2J>!^5cA+6D${7cQ{j6+aF-Vrx@8&(2Q6xA^(f;OWz+c)m~5(}Vx~ zv9kF5Sdh;W&lzp^bHZ_TC#Qo~K0p32>Jk+h$^FvD!9h$W@!p*~+oaiPaEMoy=A3XU z@PvL8IPqVqxtogG_UI9*BP=|EOUERmpT0Enhb#-b61_t;j-1x)dqDOOc^TVUpg_M+({&tn@L0!h@PxM(7)J$VQ zo2)f|nwA!LDo#Sj*!VLJ0G^^57at!Vo}&VOFf}#xhm8cE=3^E7Vb`u*<=6MHvJU*r zwN_M83a+v_v|Dih{z{7+Iu;fcL&H5g0&g`XpJZTT3&VzC*FyC}2gHu?_CD^~d7atw z-(N0nZoeZ=za}PYIHD2~?iyrTO#f=o)7RHMdv?nSY%I;RC>*0t76;kyZ3(UNYagv1 zbvfw0==}5N&xewB?A>0|+rz@b0E?9Gvew%9E*Tnoj^>UVHKir`{G1z3OMKd7DIg%w z^S3Q$;McDy{6*yB#~PP3L;@D(oR8XWPM5!k+cd*9pP zKYz>?XNIx;U*U{D*nhq}V(-awdA4k4&YZ!)*Ex4i1-p>_-pTn1<80;t`N<7shKoj- z`Ug=*dG1Dd+2V+*rJ9+Vo|yl6!>zm5ep|42%0tzu;nZ{WfHS)3zsJX!C!^I;%kigg zR_hdvlC=dCxAA*xP37{I8U6`mtWfbO`Fc_?A-qptP&r>_b3`B8@KUR6&LP`YNg%UD zX+S;AG@#F3m!iNs@kYWNj^iUsea=UfY`DW>0gueZsYdX}0CkaurrCZRl}azQ@87I) zL#}M2qy!WVkvflG#?No#X^5Zcnzim-d}#7WA+fOr$jvxACO=fE_5u&aSR4O-<<2gIIbB95b}e-^0U6xw+A(Qj@?d_zDE=$1)(Lec1mLi_gZlJSzl-Zm<72}@Ovah#vHSRJ;frbSEk z6naiTKme<>8*N;Jva|EsSCqgxmzVyHVhhK8{;c`e<=F19+YND&)8EdTkhiy=>{B{= z>{#&KyPHkFzdXNfkHnp|_Eo#3bVGOdBf>H2FBQ;}u3k--vX8;SqSISPMn$>*eO=== z@nK8)^XIflw}6@l9bbFS*%lj%jF&D61Caar`kIUHB5z$8MAvb>^#Tt+e-6GEDsJfp zK{O|vKhw{TkEA?%wsl~ykWk33gBG;R%r$3CysM6l7b{%4w0ClHavO)tC)I2s~kBO(`o&LBlI(!p6m*L|3|s-O(_n+pZ+`PPzq!gvh7sg_z2sg`(vE5uwvO$;*pD zx#{cg2hPUUjEIg_^7K45J3A{7twz@Zl&qt#uZ(XCC}VD65&7VOGRh#B#K7PnRsDge z+UHqW)ix5z->mTaDAAJ(Ly4y^TsUQ8vp-EM@fXgJS^a|pAI-&uO-esGH6E`)Pr_-! zu{pz;oY&>C&!Z$^k6p12XM1ar``K(`rHpS=__#?;ST)NNVyu03mYqZ;y#ZOGw1B9!nsBoh4M@G`)$IlhH z9609kms3nEVhg+5jeq}Ketn9qz%c`OAu!;vl!ISw6#oY8^XCPPz*zYwd2c-_FK@ za?Ex6%Ayv~0g(fm0;sctAdw-bZxdKPtG|hPW#@81sHh1|fT|*l`aq{GrjI-I# z-oCy6^VUiz1WlJq+%Fn{oY;X{Bj2M340-DQa#9Y+7gI_s%L zif@3$+DJH|?BJ;pP6LdMRzxrlyZZoLNJt3zRX2QqSLgQQ*x9$7lAP>tY6NAK1J=EK z`7$sM`ea+KHM47%J3lxH4{!&6qE{r^?$hLCcaSdpYD!w#G}xF<{t0{pvbz%#?*Xra z8v}pHEDSLC%oTNCJhXe^U%OpfzQbNXCUflF`_a*pzvAq4jg2++^_dLc*$}4q@uP~& z(%*w!?n7)3L`*aR-$`Rd=>`CC8U0zsu{yCu!sf?&@@TO>r@XwRKYaM$HCe?BsG6*w zu`pt?R);MohyMd$p`0!IyUSGk+8@iB?aG+Y>twWl0%0NN8ohW+l$_lU6q2UQM@!(R6O4odjG+L=C(Ff z506Dx+hVm;`Aq$m*4C523hnQ%U7GBxIwUFSv^aCsArD~G^IKyP1RvHWh`0+yuXcLjmpr~i_3@7`Mg zL?{yZBUwc%T3XC$*)78<85z_!9z0;e!QZ6y22~#X4u~RQB6J=8N=JZ^9CmD9JeR@2 zL5*1PfV0N#0o(UT*yGa?uz|`7!3U@hT7~<{Y%4w?G!Te81#?}VV!OknSa(2H!KN@% zfGV-o8gNY{p9Mu2I~=tUh!y*hoLy#nwpl5jyoSriCAJ+y0AI0LJpJ^6`{km+Z*Nh zG@dbF6gon0PNPgew1CI5zU()!uPquLDdAWFTE8?Zh(s*|E%>~=Fzr5^8WUbWh>i5d zcg=_0XZ|9%Ds&7^UfuxgLHt3o%WZG6a#-KHcH2w+)nV&qnp6gUpRMa*!+$X_*!rA!{ zp~K?hk>JkQ8p_E!v=6ri$e&2pHMKpo8(R)22o!>p_oSqCP!RJS`Zu--Mck*a<8hz{ zi(2kuE;FsTz5V|E`=St7fI21?ya2Bl*x7~0L}Kd2Vl}Wu@HO#xc=-4t(Y?T0K-BKA zh^^0VRR?OIV4v|g9v>h7_U&6jj6raIyt=r7)JRmB0Z2vMva%+$_aUV{|7Nvq^9Hif z+TL8&)6)Y7gzT|DM#Q9gX!_#obCtiY7Z`EBYHVyAg4l$g#=fq`64oDVlvaS&Rkrvo zo8`F2A>cBs3Z%x3_S~CR$qVZVdC73#YY+ed)bYx;^QdNmwBY`SEyDxQ4HT2KCqU*M zP=E<2IDdW@8yg$W*;lJsT1BXs;oxo9`8dQYUnKW64 z-(R>uwiNgCuzknD1JMmVlc7J^bBjj&QuVg2Tem)xa^QvxNLv$0z4USKJ&G@#onehb z6}EYMW6mw$Gl7fYv>gnj;dll%=IoM5~F&WW6(qc~c>AA@*Y0~SN{avkF{ zt;Ekba38`XyFL=C@!D(?VVuLxj$<81@N|{+^uE$=Y_!Tn3%Fa;4^S1#&;*E;(@_@uge?&}Zc&?N?4inxr>j=>UhYhGJKv__Zt`C2ZWd zk#_fPB5&e+Ltr|Lqb6?kRRCf`L#v7Jf%|OW?#ZuTN8m_30J{3w-VRufQ>7=M%Ckry z7rG-PVPGGJ{_59INr2`7NMBwkdI0d&<<`HQAlX0PGS-R4HFP-CuxUILl?xvNh#>0< zItoPu9Ue<}mqYe0s5w4*@$ytXjtSwFP8HiF$)|^kE9LZS8_>z6y8D9UpaL&|A3{Dz z0i1#u1MUw6>I!HDfkAzJW?9B1A&o=HX=z)Mn^aJXta2aiJ$V;C01h`OP;%=?tc>?j z7zKx8V`GV=fGQ=k_0NuisZ{ zX5opyIgPqHI&vtv6@fHRDmK8NkWYG&lyno=8Ssn>y{Pk6TA z;K2Aed)NWrzI`hf8lLsQsRo`wuW1GYiQab>QXD$hhZGT`d|DLxGiP?9ddo}fq@%;* zVDM%I_d@}|x|oW`64fT-8vz;qR19b$Ut3#~TZT#H;^lQ1tlJ5;K}ku;DIh=@Sh4N| zfCPL8Fp-YFY9dY|+4>vTJJ@)}9Q z6hW&;>%oy+URfC)ABS9thNPjPu??^dd*`o9QTP|=hY=4Ss^EE{9is>m&N>7Gh#zrZY@dLQn%EA3hAy;Ohrg?{7|32gL1jDN4`G()^i6}v?cbf6l=hl3~w9o^~I zr(SddsO&qTptjjmn~Osu`3Mi=Gu|ce{UH6(y$*EE)>uS|x8}7ee3Sh2Q;x?I_g3wr zmqn!)Fk^*c(mu*m9F~~aO`A|N=ooCRx|KfoQiK~v`n^_bw$u&EW`B7z{#_rUZWVU>4-f>vT?V5OlzB@#yPA<%N9_1#n(=jjU&0-$s736)%MNw*^+eT2 zIn#(gx)XvdPC-FI0TCX6tCEWo-tNJP;_zJ-gL?-l!f9dZGSDzEryno;DcblsR5N>f z?dSUdH-J5Q0cgmgqFg-g=`qFWCED0n(Kw&9G;3S~AD>*NKK1%DX)P-Pd7PcoiPz{i z`mXe-J^jdG-Ml%rZibkD9~nNq$;(wdt_-Px_;2y+t zG>3y2U)1pUT|9o;^0ULoAP=LyuJ#yU=O`?$u2>td`3_Sop6p&aJ2buMUbOmT(QwWk zzRp!UyDMWI1q6p-7f%MtF5iTk1e9rC)JX~`*w%3vH6U5g83)KG7Z%oZ+pQawq5@)_ z4EYI2pU4w#(twc(kaiE+bxGrkYS)>IW1WHVP^}#Qd=)e^Gqbd{RZi6<9%SQCKXz`1 zbIU0OrYPNX!rJh*bZl&=(4~FnD>zsn@1wJU711*@2SU}G8mPrak4E`H)lr4aTUhuA zHYa4>BZ?&}m-eI-7e9tF0YXH;Aw)7frXI%vsKan(&0e2F!NcEBQr)ZQ<%ALvAkSq+ zqk3L=Qw0hpsuxu&4}{U2D~%x|l7|k7Iu5A7Iaqxb(!a#8oL#zV_inAaB)hEo-pZQE zLYME9bhoe8o1=+dQ&fV2f&{litpRugsD{EkjgtSyd&y-izkdh5HDTA};dK-^-PwIu z&0dH8O(qydnXl~8_#J62q$ojAwdpR6hgZ_v+Bz41k{Cl88h66e(DreDu3B67&y}qm zM^^)|^uv3hwffi#9gEkrEn9JUk&zJ`8k!7p3ab|#4Ud_r?vL!su$J^>CBuG$w?R*z za)X;Hfgxb4!hv$c%CGedtol%I-#!TF!z%0Z7!FWVR~Mlo;Kh)mU%O43;VXf;+%5L* zarysQfV(?@m<0p{>CCelEG~_Al~h(%QogDhnSFzw*VWZUdtyD}=>OyiCk)~P2M!Q_ za*u8P%}m2Q`kgyxZ*Aud3jplIn_^qxqy-cSoDW48#~xB#JOO#mB4-z>S^Xfr<#SY5 zPEN>Zd_68#-l^QPzi*M@;T{#b`Ne-jdX!;2<-zz*OUMkSzlw?P;_rbM#dnj2l<@A z&#}<_E=BP%CO+rqzo5FIj1M>-!D4KLq`LmXQsUYI2mS&y0U%rdT-sL1T1Ga6hMS7A zC`wz1$L25miqjE_CTH%~r(G8tjJ+n63X6(hO*7FJG+FW-K77V<9i*|(L`q0f2!ww2 zEF(jmGmPGjryvrPhd8r1b&mB1@{mEGf@%%zFQ*MA8eHpreeNmGT84vygSn0$k4M!8 zaD;mT8%1%Gn$B2pzx4b+2(IYie(;io0lT)X{f;g}% zi86R|3p)YAkmJBDR5UayO+|zJ<*06hVi8(@p~!`fmi9eFdAK%;Cr|doCdXm?vASY zDdBh=Ug6KkNG+HlG{dPWM}WH%g1(-r1 z0!kyL^gTKe`8ap(q1!kR-1<{d31I5<$xQ-_-@3c+eY1j>vRyUk{(Jf`<%;>qekG6a zx9b4THW_uJO5q8|NnC?5?+DlKoo#0wn`?&{j}OFaC>%~b@7EzCVtMV_Ao?$G$1A&T z8Gv|;oP{;I8l2?t>S|>!lkvZQ2Y{2Xtwced;FrNP=GwPUJ%3N+4lUh-FsGV+{uDA} z$ZJ2Pth^ci0rO)`TiYxOspggzRV}R{=Cb)sH%#YK87`LlQ~5girJ-mJ%)%dE9a}%+ zQF4d%$W*r@hcN;UT-jF|6ILX(CPw7KQD#XDLQQQeVi3}6%hSZs09gX#I)&N`guDFb zY+1SGAxHQTt0#p?s_E9PTQ;4A(I}x)aox+e(PXEAaUeTTqSX-%1Wf^yjtE9zW_cZs zq1q*Dd&7GmNfYN=mV&r<^HA{IXPQn%)S4416(^EO#P|*rSiIFlj~sReu*nl3d{96b zL|-;0Krlu_A=(Ut!G%8=+4e`{iT!hIEdLhjJHXNruX$0L<1@4?D=Ubc+(UB5Hotc> za6ht3Hf?VL0IOhnpL=UbN5J|CLO8ji%sX#46JA#!6xDHEl8z>$6oo&gizT6uV z8bxfe*OpD(D1fipY`n0krDwmMCglks4q^#c^qv@VK6=DwSqfP$tSB^fc;@}sD}e2R zfF)hNYuBx7T^@=olQMR68qMHwk&oEb z>uxMF%H=p;5Y(SfU!E?@jYzp4jrTykL-E0qfjJSa1qTWI3!wv22mpxsN&Y82En%_t zQV=|-=qm~Cx1o;zYKS|D)DZ|b5C%OgbNQs6)ur(ogalv*tEy4~>iD{TswgkN&6?88 z3Yi5z#K(95ay7OmWd<`NW95(6m#VI2f3rgP3har>-~?ZknDzJlV2Mx=;FH1ohj8!< z%?DM8=z@!9O-veL_du%qjdd8!~7&`}G5u^s< zPW^C88mhr%#1WqAzYn6@%L4Bs{HCV5I%&#i!WI_KC>Kfp0oK93h|nJS-rAaTtzF`d zaz8EmpRxd-6}_NlS{#2|s|-hu9I^TNHWzC{s_$TMo`$+Q!)|RV0mq~9ej<;h-Nm7}{QBLLyuLi9&w+{)ePZD5v9TVM z-4jXL;W07%<|j!&h2(vx5`oSL)`E$W7-Q@a3^H%uel2gi;2^}BIzzh>B~W1UdZ;-_ zXHZe7@I_JC>NI<+sm1UoxcM2{76gE41HkHlGK{o=lZO7JMv*`xAQcS>I)lsy>8I1M zHL4-=G>ml?wE;vT9W#V7hhv1jj{OKgl7OEwlZZP4dy>O@CW1B{G7WpQS^ypoGcU-vwaa7VKuBol0zoI=vo7pYe7t7&7X5JtyY$EDM%l)^ zZXc2<0$i#YcBW@x`3P1`j=({SPb_9POS^gOuu~w=DE0M1Nb&FBKXmARqs-DB=-vPZ zzyTnB5p1mZ@W6h=lY*spXOHBL5@RG1FQZ*{*jJEvAi*v8yqaEK#k3oJfxzVXrJ!`< z7UlwBo<|0up7^w4$M!QMtb5s zZL3P%^WxG+pM2j0`TiaE-4?cJXD2jlOcEI|ME9M|nt;{x#;j^9p1r!a_sSao9vR4^ zWM{zE3Xh8m1>DAZ?LYr!faC5^x5rwVbNw2f!F*%K(D>{mX+}_b$jAKpRS%qD7Yoai zckdps9dm)CbhmxfqPx@^pBI{kl<%rEWD;(gKPV}L=OQ115`>HZ50(s%jBpp1u?|>9 zM?oJ2ki}VfSnh1Olsy7bLgXDBjWv^OUJ1@cQ!%_7358Bueh4aHW=P{; z-K20RN!Cz7O-40Ntxt8elPY4fn%a(OkCI|QRT6d5)s@%Li3lH4$*Sq@f9GR0^%nXZ zv_O=fBlbNMF#iV;$%IHPN`&0ck89zKPI#0&U4FPR@E#Io&@dws5`_Cst9tE1U@=8C zibNg&-@*3~;#7hxgTf1sH3|<=Gc7qY^OUrcnHe{TJv1y30VL>X@G-fs>PEIMAHP3d z)3u}}`Q2B|$E1wO=kHGlkmj|KynvIi;6&~-MV@>OJORh@T&~ql1Xtix!zD-D4Y@_` znEC>j(cRb^q!ge@CTaV^Jps_;=jB!6jIV<%CTAJjU_p8ls`361Ct``h@!`_qfI4ZL zXIQxj@&f@{$RNwC&R>EpRatm_^R2D)?@&j2eF1E`~eA*7{%zp*56+e zRQcZW&=eYEj`OfCJZxkS_QJmgp^5EY8FMAcwW}?B@b5PA{{VA=VSw5PoE4N(sT9gY zawj@FY#I}en>l0}iFCQOSY>oagE23e5vId#@@Bipt2m#W7&WSCI z#sk6<5ZN{8NXN{Kwi)yB!PwXs6Qz@j%e$U!)YR0$AtBrc4vcbm2+?n!UTGMbUO)t* z!)v;Mls=O4FfzJ>u6D`S`(>JL`uyTZc0heT(yxGkOrc6oI-nNuzDJ`%7pQ5ZFQr8mz|nXEGe!79 zp(4a;Bu$q8<&}|?3_N^L90Wn&A?5jRKaP45JV9Rd2k0DgChdB}f(R+QI(hFgP#N4K|2VtS^NgE@fBz;l z#&fJ75a*3+t{c>oWC&C>G|cD5I*BrYWe#rn2SEfXa8TuYRGKf%&D>0*W$io{-=Eex zu7sn23S*8QNy4WPsYAVoWkL($QtK8RDp)du6%~fCc?AvU~Mk z-p0+F9ec|+K^7nn2WsatL@{5!e95I`zj`L~39{skjdm(mZ=n(B*b~Te>%$G*bVeoB zdZ=v&uk1+l{EuZUBzY@(pJZlkhl&E*m?V#ZUY2iOj%2Tcmg&U=aCPw_sOoVQC9~Bo3SxEt{UJsS z4zv>*nR!l#4WU)#5OAA&rVSFh43$(@BDU{pz(*z&vsaQnFukK7ZhV2h%=!{m+k zrpBxt+Y-iObvHD0@4kJZ&@)3kV7f)4=SC(Ze8v(5h`u)$N05dHpO_Bt4-90Wr9FYn z2TW%Y%S0;V!2v^M1R@b*LCu2QjXwTXdtUw9-7IG7dUNr+tVjHikDzDMyKo__evq4o zXJE@@tdTH3ej8R7095P|r)M8&=N7zR*5C(li~i@kp7RK z=ZX3XEfP*k5>!HPVtk-Y%>TSKhtuBb;<#}O2&kOsZ;fd#EG_7?1+Up8e|?3g4B-hv zVgT8v5T}Fdu&>TnHGOKNHM_=KJovtEu#>fojd{~kB@CgIF8j_T?xrv~l zAWjG+aGLN3LfB!dUjjVAjturnM}{d1;qnir^K!LAcuyi__c9G3fB=z?YhraS$rnxv z+Ch=aC}Q6Z5FFlkEjR+)!SW_4>is6Ak8#2^>}qNhhDiI6 zTNKU8LoE!X}U=b|w@e!>XJYFEKXqGzJAcFKIBUIWMo$PUDtpuA*9)~zY9ZmGZK#J zIqtKz)J>C~N(a=9;RWD7qHvn^yGyeZn{IU~rfgfmyA=2RA|gWww4}Xz$3y`|&)2ss zd~^CYD};^+Uqyg}6j1I?xt|oUk-b(IhVF348t1q8iewIQRE0Hj=_5^OX7==>Q7Nhg zs^-b$CWvtGe`$GndErvMM(@;_>$E(itFM0>qBERAWGs@d5JRiGI}s8YUCaHL82G&) zS%_R2-q;=~j%2FnwV#K8Ct$R?mS)UO?0tKq({`w2uImyW#?uaYD5R2|&J0?|XBi0u z?kv2H=sjCZeHAiAANudfY68zfEbH(X$>jbujZrDVnEyNt0PKF8BhX1qy`0AY2W;8B z0s=v3c!**Y3?+Cz1m7VkDx4S4lpS&}prI)4>cD~D&r~1&Ax5)>Ms_(IezJa+kzjLg zSy_H|%$rYflJ}tdpn8D=BB_YhcpNcFus$;7LbMlfJ2J3?owxWq8DjAS0CKQLo9+X9 z3}2vS$_`un86NHh76pYtv>8 z0hX}panrK_@#{-us0f|r|;12x{Emq^mOfW=LFtrQ2^VnKOd1I*h*6h_zQ2A z=!|F1@ES!DG^Y^RnbjJylZgq~70;euMkWDNAjnS~=5xDkQ5alic=jJZeq>o60Ug2~ z^h{=XLIL6@oC|#K$0%7k)qm5hB;vLg7zuB^tul%{g(={l^wQrP0)tWI?}5(CU`EKc zV2~-xsDL}=pl)VqS@aJU*xezLYUxbiZ5SmY(N@&O=L!g5Qb;)tP-f_7_SNzy!ndZ! zFb_7&#D%Kl4O?~u`4{?DjTWu89tCKGh=jn`j@OLnX9P_H@sPd^RcV)`E$i#ouZegB zM6L0)bI%b+9)u>IJ&Zx!#88)j&mDQSvIvTJ6y=By#}MyUPTsXXNAV|TyyR58=N+o{B zjvW?gYZN4Ow#IlwQdIN?Ch)*XNURWt4#lyuaZu&;$GNIk`Wa{RXm{glA|%QSuP)`D zI&a7to8(Z90d!>u#1Qv^NW}+otXs1jFgUl;S!QQt)t6N?w%F7-H`-oP>b>MMGks5H zF$n+s-ZEZBf`s@-)~yUs6CxOqxB-Z;M*(w})w2@hlV}HPQog#?u4jj;jDAUm`2Y!^ zSD-dPm_jI>yA$j)0MGt5_!=D}qkokdNoIi@IQ;v2zWN@A7DW2+hpm=}$VvnC3+y`J zEj+w8=gpgZ6sOhR-BI7u^sW)k`t|EqAZU`92c-T00Uc%6YyQ>z#V|M$aK<*4Gs7nU zw02DIdv1`)hfWH|2dXW}i6Xaxy@ipvaIsN>cJ81pL%>z!9dbP z3zx9%P%$-qq7rfqAqE7Y0J`Cg+9bzgA8ToCZ8fIk5S41=ERU}O(S zNdtyNAz&`cpEw<=wWe>xJy-|lfBN&WaeHXe1naLWQj2{anYu{wvW3_8;gmkj$vJ(W zKO-aK5`y~3R$wHOTk~Dw(<7`qbUqGvjHKuZ0e&sWiLLosd?+*$MxM<7#o}TkqVNc> zDm1_CE$VoVRx`PGee-RE>=)M6@v?1%fB1WL(N}#1gRYSCQ?s+Ro?OFUVki*Sw;ZF=U{CLbF+d9 z*NGdPO5sA>Pq=&53x_bbbJx*b-dW}O+CIkffVJU?_jf5n-uu1PmJig{<)jK8J|0zT z&R1(LKDcmeX^EYiv!}ny^YgS<<0LDC1z%bBa_Qjdt}2V1*Ve7VV5sn$Ae71Z%}!5O zoDz;{$u^OdS5Sa|teCE+3u0@K`3tfZp=B64MMHOoyBtv2YDe{AS?AK1CvwESg58Ta zMZn|9ec8p_AFU(nuEP67@QK6`G#*RQ1;~E@0}v1qVeWzm84RK8qV2zv%}05jT6lYx zJeLMgc3I!Qz_w2JV=#6~ntK{PZV zCclZf5iGtuK)gs^f-Kja@6K=NUHU?EYr zBch`APQ8JqdK1!a6uKVZ5k#OHw6vKoUozg^<@@!va8xar5Zdk*Os4#AHdr)SD^Z3_ zUMS}3J*|LOs{E>(%{od*xz#iUIj$l|MMq;?%lfrcMSbF zR5#bTa8-w&1pA<6$V;3mTqSz6bnj?ib5=tzoHO`V;2S{*>M3W+O9x4L~>7(P30f>#kDZBT%AA@)c z{D2@`&406UwdmMnMhz65Ol6|NBHG?$d5GBZ2!?LkTybs4!&Mv>x9sZtUTD{53sZw+ zUI+0Bxj0#;Uw6LTYOJrngpLEH2i`9Z$fGZhWA-s_#W>M`x3nz_iHYBGNT9ReHWJpeGmiA>2&AF&b7m3kFe z&K!x?1oIL+aDW$22U`*h9XN&AvWIvmpq;XBw_MI?BU%Wf{SAzoK54S__i;nbg*uDL z5i+bgS%}#JO#V8ERCNnDVx<23_2Y$TvAnT#4j`~+Je=}x#M0n@z~Tsx~EcoAZa65vOTDhV@S5IB<5O0a=R zRPyeB!47G>(`ZK*E4Pydiyy@i+R6QZ0`HW4P8$jopw|R^#LxiFYuj`M4R@1i6y%M; z4CNns0v7o~EIyuJR5V@5pf%H+5r@75f1+%#n!nA_VE=;=$2aZnGEgGnF(Q>phGNU;<#? z5>q#T78M!Ur63d3h|v;Au+)gbg)iT}Rlz-V8_CSW=((?D`tr|LC!1Abl#x@!PAg%G z(v!+}QMqGzm88AToVng9PbSYuCLDB7?=6B(=gWMK(3LW^|t^yLJ5f{a3j z7;VpULJZ-)8gFT7DIDRTttNP$LeYN;xf?jv?TxzcmuqkU)EBIb7{$Ml|-xu_Wf{so(RTUNHb<*+x{Mf;&x(U;*+tpjPPGV z(J#)Pp4Ok6@{GEQ>fyJE`bUv#_V3lSXV3mEc97c$pvOiSc7C?tEC}eJTb@jfw z$3L_ez`ic8=~Lu@VOY(7!MV(5#a|;YFfi~&7!-Nvr||d4D30{>r-Kmnfs0g6o!WU$ zPEu0Rp_~3%SAG46>xH?nX6h2-M%eract3mcE!*g+z0wD8TJvKPhULqo0V$Cl@2lXQ@6sN|Z4raz0n~&E!~c4$nPx8;VdI2!2cpkNHTRsv4F7Vg z?+P>8#b~ONiILH#V)tpqM4iI3wNl3g1=C}0SFN=x4fgj}K#L%_6eUbvTCdOJItB_b z_=33H#&EBRo)3_zZlOGL#;`J@#r}Y|0;uNZ=}9gRfH%MEn9F`VDH1=yg3wj`o0;jD zd|G%RsWPrN%a(B~VuQU@ymBr)a;tkH>TD0C+ws0~%i!XY#8oXv^q98{Q zM|oks|6bK~!%TgW0lzs@7T-HEvXArB?yz4++2-5b6QGMix=$(=!WAX3DoJn?(HY1| zANCm#kxRtb9H1Z96fi}rRe|@+Bj6}-;J{@l&^A9_-Go;D3a&Tg3&f;|nk97yBoMU$ z(@q6Dc%6!Ne(jb&rLv+Bro1;O9IuQi<=}!c%*Y`KhbchX7g}2b{EmD6r2q(tPv5>}#3@uf1d9=f zgvg`X0wgtLk#ph9z;Ys6-LP{r!qwW^+9Fxe1NoEIbtU&XR4h%e%B#QPOHUWP5H<5< z%v`5!)CGWBF?A@9=_`jAcDlcF?hM<$Xf>EiipIuW*R0Q~Y_BH*y>>y=(t}!ad1P*l zVYc%kHbi7U4EQL_yI=e9YMq^(9l|XqUc$LEeSJG_NM#3;# zy2VCfx?ZHrh~L^ZXA=^=8;d$%8Z$C}-KSC9))!f8jxYi?AM6-6x%xpzj4$n{%%GPP zIevWQMXv!-lWlD=FtD43hNhRT&|}sL<>bJfs;u0*1)cHVhn?SGMBliW?J6CKoq(Wk zeft403kAl`KN7;r5zME({c)W)vJ)R-f7URW6#~36`|~xuT-y|@i?q4Mj2K4O56eve zp8uCF!R#VQw_sOdO9iVP^MvF&3`7Z&Qn^03`m8QofoDn_ zQt0HE=n!?AFa^*@u;|L{pKo~K5VfZ~mpYr8J^`mC7uaUKH>1~5;dg&@XY&tYGG*! z#@B5l#Bp)E3e0MlR>>GN<+Ir$ENV42E5M%LAZx zsY~0a2K@rUn< ze)q_qKa`lZKtTQ(zABk&#Kyohe3Ml!8K<&olUG*W47(599}~&vi``!TKBgKrgd90; zUitm|_j^-O;+=T~`%=q5{%ypTLud}}{)Wox>aAisRYlfXuZGUppr>Lu5&;g9c0y(i zw_PY;NIRzuTI6z#@A4MdU5EmQz*#oh&YY^P+P9DGs52#uF7PQbJ&c(G8Sh2=zDg=C zw>8<_pYzzb;V~dmX)CoWHU6ZUBRI2XbYgbHH^?32q8NyM1G%ln8?xyCvhE1{qKwHb za&#ek^sYLL2KVDi0>=i#JtwB7=%2OYa22nuE|K(E$=7SX)`2q6Igwqyh(HD8A?zIP zLkzb1bjAOA1sOxy6DpmCJ`dulG5Hq3?T5rqlzt$5q0)Y0TOw-ZGv6B+m*D5UIKw3& zp?^pZpD+Ezi>IJvc_r^tl?K7W&~4$_FnahS3g)Lz(v^>oIH8T+4j+3UY9DDnjZwCJ z5@QJo?7(=xTeCR;rJhQQ44(#)WiRR!cJ8$M=am&b>T)!mco+a_*!KZZpBjGIgKWV? zO+z9avp$r}^8kfpVhh)`Kw-iFKgQ8j@b+0p52N`zD?ufIa^n|yEvL=jAvb0FaU@u9 z@5ElIWo)eS+qyp+?B3;ri!5MfSPtFumBW764iGhapzq52{e?f?gZON*0^AGLq zai9&5MhT}!5g-xZLyFyy55dzAvHNm>Kl(mvUS8g51A{uO0QNDS^aJo6a5CHZ1o(g? zFc`AsJnlzvart*($&(PpZl9&h`MZXOhQw>Z1Vl0vX7Cjt`>No%FA6lTG0=IlaBUWZ z!W47qDZN$Lm)qmU7~K zQ5}?Lgret-h6l*ja{rdO{4^_Un=PZek>Q=l7olx!ZIF(L2MCY661y7)PI7v>>cA&m z8l68>ySHsN7b%|b8^J9$oT8$DN|*T zEqsgb`#$zoZQgKAIN*q6`>b7FpVKkFz5lzTPXwVI5JY0)MLMO;!P4NKX0(ASAx=!p%%p(!;Tdi?8y$k2mVaE_9^AkK$EzzTGcydv z{0)NS5r%?Zg75LCss`~I(xkVsh~7Z5g^U418-XG6@%jI6e~o*imJ^UB#pX9Olj zTDw#?oO?5hOx6It>@&=$K#6GS>^ub^jVY@v;GDL#iEyJEFA-Eg7a+HOyuJ~w#tS7u za(NFpE-nlR1msC>9XB*E@OK-`?FWviG#7_%{nh%Gil(MA#uH@>vyi+-12d0|IfD{} zhlWZB>ke3Z^m_SP*YgUC9ID2bdsM4BUy7W=&>DmQ+|HNW6l5e^cFErzp(}g?be_+N zvLZjFH*DVad*^2yagtF$LEQph?tG!MAR4hL6|aInRs=J10#h$=$H|wUKSN;3qP#tO z_AH|}<15?P-@oRVg~22TYk|>cWb^zdf@iis&JDmWA{jx1fyt~IVu_RiNr>qn$J(U+ zk}XS3Lj9c($wC+#86fI)`a?O~4g5eUc+Y z48bq$I@lMPafh%@6moLK1|IU|k?)yEO)CVgbbQW<$eJTl@*lQv@F4sEsTsa?4boQF zkLxLW5W^~R6@ig5h)dJRd_87bkfwkB;spZS$n|^1QXoqanO(XVf{H^DmSpGN>;X$Z zyP%DNK@JVlb0l(vqgNl!r2sMP2zCW_APHXq&|!k<3Mx0!J3Y{#9v!wO_l`k)B9^q9 zyE_DlvXOJo=nq}N$0qI<)Eu&YaxC?Ab>I*8aguPS9dW|Cy1IZO&|L-g@8=N_xreSU z=00WK8_9XZ*%vZ$F=QTiEB5doHq)?cz~X^cNpHFJ)`#~fhLkik{7|A&b!&;!j1c6; zO}+XwFL6>}8-Noj?SsSsrIDn_upof6_P8se6}Joa{_9>_>4s)skfJo}yQ>#bfj9VW zZQ!d4aI2Ayp(`~8)y0`oQ3;y(6)p4<2!+V5P=v8fWQS3ac#AU z)PUc=epQ3EJ;(JymQDfkawJE%1f-o~dix%pJ0y;S0Ka6yLq!Fl7^*}uq#Z6_=EY_s zqgdyDsI>OjOObIFXpV%AW3uDo1pmbe>_{nGONHbn1&X67S~eL6fc&<)(!CasW=oQq zxH3ZyHX*7xjuW|gCI>`?YgqfbF&`| zK=5J&WN>{Q87t_~*vZHkjvKieERqWgcbk})czJtoT5JQ?!Ce_3zcBSlkg^zeC31fP zHA_X742|s-b~c13fM9}7mXXaENL*Xy2Z}}C!Cg`}jI+srF1fA->rHj04cmflyc=b zT$Ql}q|xNk_398_-X(5M3DG?2LVMs+84FB#qH|_JT0V~?7B2QcTpnKr_zM6I<7E&= z;TGwbnB42MWq!pqyhH?GLBU{rN^odP8=C%S$NY3n-Hc`wme0RcSKtw`JjRKh>6$YqD^$$G2SS?s9FRe z6T_{I-`VU!q=5F1R6e!$3Co}tm-_Xhg@SGw4JxRPZ3oCDj&uIu;?>0w*rb$H{OJ)w2k2Erj$r@|;Tv+@ zAVNYiF*>$?wFS{FnAR1 z^rp>5KC;b5V(w3&`m1fK2Vu?LhBO4aXps4i`J*muFcv+vt-jvt-Q3(Loie&ZqV2x# zT+6Kf9VTiR85N|KS}1H+*wmfdK8is<%8(@-8zlM2eOGI$6PU^P??RZzN1}?xOZVW~ zH{|`RNE!zh2a&N5+yt~zB30H-waadPH-MXr3_9wX{ z>-IPdCvw#%67~8SyC7XbGDLR99`{lpA6}0IajZDq(Q8lnRSEJg`3iTZeun+E*pwW% zF5CBlbfFGc?V#f%k?Iq9PrtK{E5=kk4g&VR44z5btBbenTkM^j7y`J5Cm>0NJg>%$ zGC1DY1kvZj)NL!e9YNJ+6^1o2|X_dGk3ix%FQL4n__cHSM-<;A7I z$c|vky7Dw#&$&IpaczdTBo8+oV7-`5nwj+-$Uf`W3U>^pPMB#8sxX9(4S+ke-oZG> zxc5*K(F784L!`&=#vG;%s1>X14s6uY(gJ%92rsQ4j6}2~t)kZ+N|q;_^0+E9hnzN> z3qWj+CuTDm?bnIpvysN!i95TX>oa=4fX4tpbgRwAqUZfhq$J4gsSORO2*m?ILgK;x z?tp}XZuIX(wS~EPP}R&x0B2KcQBe^n0S%tG-zNKHwZEg{w6^btJ2g+wDJK^dVR03) zS^&JntbybJ>dX@;4+xGX z{l>*YLB=M}A;up)`iPWf!zJR|`uPdq2Asme#k>Enq%)7pDc|FGqDYps8QIz%B}GGb zUUcOum7Wahk)j%r8j+=l$TFf(mLl67#XKn~d!!OCl^S^^OJ#6PSDP#;YhxR)?)&Th zJu^LL&N;vD^4U(zkE)=j95uA0WGJqi zaSoN4e|Y!KK=%c6o>9XR+!G#`6}f2~o?$7l73Ah!MKHnoxOQSz44go@*{0%@1cPB?suLxV~gFa#t%yM-z6eX-6hZ1vpw> zI4IA*E$7Uc=$da{?@K3qY_xlQHxa#V(xF2E)2B?CGC4Ff^Cj5tE%>cv`~=8N3=h@` zF-&U=+QCrlapFudH(@m}JUv){*fN;xkDopzY*~+OihP0KYATOpSS(rMcFGrxX#CTY zhKH3dBLIZ#!B`o@>vJqOg5}%yfgJ{Jwm483Z#R{(96|@me+=*%j3OFSigA5w>)N{1 zwy3oOd5r+6Neg=rAx>W;ZwW))HA$=I>*PTUq%}<{aW@`DvFd)fh z9<%tGadtKAn@?znaa_!A78qs`fVJkV%ir$l zm+gax3wxm_2?%qY!DbVcuUcBRpj>MS*i*Mnl?}t??bAsT1XmoK-;+d`OqCoIBwqY@ z;H9Vp;3eJ3@A0G{1$mH}VP8YoOwPx=taBH}DC>hbE*JiLrfwzKlXrd+o*PP#nX;15 z3Kv(`I20>41T#m~J`QIp$B5zpk6|^_ICNUpjBTj}g@tb@T6b$|nmngZ{}2%!{XuZL zH3*IXcF2MH`k|fqWeCLj>8qVzU*)n#5g6wTNV@TrM}+Bflg#k_r3;GccCp*BS(J8j zF7+p6QP+BRt(D5!5X-$_^>0%dshx-W+3eFi_9S8~f^&k<&EoKJScHw!e`iY8MCuR` z#NX#OV*~7E;_&R^?vAT-D9C%*H0C)TAoPsAgnV_TmeC+N{nDUoM~77Cv5CET{aWu- z*M+gOZH*~n_y$}?p7U>QZ3SS-0?C3PhPspdQT}tRhtf#iln>~o&Du$Iz~(2(C2$>t ztDk=e1$Nb|%bwyBXbPy2iSaEwG54cn2^z6G-nqu4+8FC;>iN83N+&eUWFBpgE90G< zo?~9PVhPD|P|a**{uJ5!(L#o)c8?3X32H#BsZ6ARmgfC$Qt_AOOP(=*R;_ma8`yah zbRUhkG<$mKN9CFfgnkodQJQ3ihUtR$msBBMl3ai@_!i=^%WG;2 zdVDf7Q)_dH>6k-RqFNyFhjfk;NOszrnkJ#OYNZ_|D=aOO8EA-@XF$-jx{rp7r&*t< zoH(B*OTH2*p6~Z(=skS&XdnXxH#FK83Bj(e#%@^jg=@V zDM_Q$bD%n7!pVD!w5&f?X7SFsuU=hnXJ18SCGnna2crnp;eUi zM}_+G*UhS4;RI#v+GT8&%6`mq_sN7R15_(5571mhw58~M)w93F1Tg_oEqWBArup>j zXwqt&LuKLQi-^7o6a#==QtrX&ETV1#Oh_st(iH>kRrF3WxKfAN_jP4kW2yeQX$%XNDAzbd{G^F`7z3VM)xbuC29n zsRhIpRQTDmiA+bm?~*VBi^&v$Q^RGH`8<3?c>A!?OgjF=om}Lp&2%dI=3ACByaHvv zXZxN&0R!oTrVsW}RJSbT4H})y8gj-LEqXEY^A@y%Ecxg-%`TA)Ne9!BY)8&@aF(yN zp;#SQtdY@6#o%=S4m=;(wdUIs z%-;P>19c+JWMDexhk2;jEVPVIA^Y^Iu3t)r2{{iv>loAC61#=Ew z3K|n+psx?A{{;1WFit$pH|LP_Dlc_*?EB!K8^V-l{ii%Ii%I76i(=Dv~hC93Pjk~4^UsEve9gH&amJ?mwA zoVNt@Wn@``1gXt^O(HTZ=AXt1~61k+CDCS zs_nRyFAP!b7B9^|4^hj!6&JQcXs{?p@LG|?&%$q#Xet!a>Ve(dn`9^ z?K3!$h@{|idKgq7K)}Q21KjXuL|HP=@g+O~z$ljz3X%S@uE@_}z2dIhjUX^3&*VQW zZO}HgWey6#-OD1*j@lREu8H+qyb|!k2IT!RoM=HvGFa+F-h?k#12(d{QM9menA%annOcF ztY@Z3;J}V|VTllWu&TPR$)ls*rkC~8* z&W9f`sL0@qdh7d$`iTf$AnPrOXk$Ff&CNxdF-)P*VoJqGCONEC;D(ZvDk&^*yLeqh zEG(gY1dIqjORgU6NeuFQ&_MK#q=1pDZWe$zE&S`}4saaF9YeZ9`{zbWCc1WS6NxKD z-67sO0~_F2dIEm2Yw$mDkHh(wnO(&<;$a3Amd1TL%tlRPkdKK_Ls<}Lqc?8eB;z9z zFcL}}krfteQF@_CSjA%kmKE-nk|iGs z;pbo<)If;5)FiKvXjJK{>~4F}BzTjxCUBCCO(WeWkiaq~ zWC^x7GGRU3Um4M=z9*2BNp2^|S4wKCZOCQJo^IC75o5VTar>QrX#0678hC+NIDG0% z$%JKqm>W99Y!xpNgHn1vqn-?XERRMu;a`_LRdzG8 z3{bPsZ@7S1UKY?XMd0)D&q4|KC!gurix>JI`VSd$iz-Uqjl`FsS{DSA-2>baY=VVD z@)|W>0`VRo;H^jXT$nxn84FcIQyo zx-2AHlpRu0KhE^q&0oCVfx(4g+H8-vj@zl4=iMCKMpvSd;JTNC#d^mgH$em#xY1i- zrFmn`Y1$b22Vo^xgYwS53|2X-YOz@E4Fjid1CpJ)OzK3>Fp+U|FPNGa^za zF^0#xWFvda_QAq$?fHo}Y>;D=hpiq*g*Ql2^T?gSmGQm~Alo&!y{*lzaTQA2kdO@P z+fz~ka>n!GB#d5*@UqX=Nrpy3!uCudH<#PS7$*09)(#)VUe9YJt-eoZwUJNsn4OC| zpHgN%(8MI}=dG4GqtcRD8<{G}i?Ls~-zG*C=~jA0sl5FDJkHQIUFGs09Z%UA>tYVR z&<|5r#Syl%g<)axBS49qb~b5KK4d|Q1EGZ8z{a(I!`II`Q@4maq^8_&h7xYv*v z2n{(U0P;N_AE&MKoHum1B02dvH=N@q$l&F2I8=Is!pds$_}l#b|7T5{8h(qQtz+Vg=9K#Pn2YAJaCV0)I~z z$B>MBZ_hLGGB9v3FUbCXZhLz(o6qO-ZeFAVE%r(G8SAxEHyZ+tX7F_Nb6Mw<&;$V7 C>o;ov From 933f866e93cbc851926e4ec88074dd113939e59d Mon Sep 17 00:00:00 2001 From: bsongis Date: Wed, 26 Feb 2014 12:33:47 +0100 Subject: [PATCH 79/89] Cosmetics --- companion/src/mainwindow.cpp | 24 ++++++++++++------------ 1 file changed, 12 insertions(+), 12 deletions(-) diff --git a/companion/src/mainwindow.cpp b/companion/src/mainwindow.cpp index 596f6b78c..a988870fe 100644 --- a/companion/src/mainwindow.cpp +++ b/companion/src/mainwindow.cpp @@ -673,23 +673,23 @@ void MainWindow::saveAs() } void MainWindow::openRecentFile() - { - QAction *action = qobject_cast(sender()); - if (action) { - QString fileName=action->data().toString(); - - QMdiSubWindow *existing = findMdiChild(fileName); - if (existing) { - mdiArea->setActiveSubWindow(existing); - return; - } +{ + QAction *action = qobject_cast(sender()); + if (action) { + QString fileName = action->data().toString(); + QMdiSubWindow *existing = findMdiChild(fileName); + if (existing) { + mdiArea->setActiveSubWindow(existing); + } + else { MdiChild *child = createMdiChild(); if (child->loadFile(fileName)) { - statusBar()->showMessage(tr("File loaded"), 2000); - child->show(); + statusBar()->showMessage(tr("File loaded"), 2000); + child->show(); } } + } } void MainWindow::loadProfile() //TODO Load all variables - Also HW! From d465ee80a2bbf400c96508202794b7202bd79c5c Mon Sep 17 00:00:00 2001 From: bsongis Date: Wed, 26 Feb 2014 15:21:52 +0100 Subject: [PATCH 80/89] Indentation fixed so that cpplint is ok --- radio/src/audio_avr.cpp | 2 +- radio/src/eeprom_raw.cpp | 54 ++++++------------------ radio/src/eeprom_rlc.cpp | 89 +++++++++++++++++++--------------------- radio/src/eeprom_rlc.h | 54 ++++++++++++------------ radio/src/myeeprom.h | 4 +- radio/src/opentx.h | 24 ++++++----- radio/src/rtc.cpp | 7 +--- radio/src/simu.cpp | 31 +++++++------- radio/src/templates.h | 4 +- radio/src/translations.h | 10 ++--- 10 files changed, 125 insertions(+), 154 deletions(-) diff --git a/radio/src/audio_avr.cpp b/radio/src/audio_avr.cpp index 356e9051d..9931269eb 100644 --- a/radio/src/audio_avr.cpp +++ b/radio/src/audio_avr.cpp @@ -227,7 +227,7 @@ void audioQueue::event(uint8_t e, uint8_t f) break; default: { - const static pm_uint8_t singleSounds[] PROGMEM = { + static const pm_uint8_t singleSounds[] PROGMEM = { 70, 10, 2, PLAY_REPEAT(2)|PLAY_NOW, // INACTIVITY BEEP_DEFAULT_FREQ, 40, 1, PLAY_NOW, // ERROR BEEP_KEY_UP_FREQ, 10, 1, PLAY_NOW, // KEYPAD_UP diff --git a/radio/src/eeprom_raw.cpp b/radio/src/eeprom_raw.cpp index 5050f7cbb..095c18fc4 100644 --- a/radio/src/eeprom_raw.cpp +++ b/radio/src/eeprom_raw.cpp @@ -545,52 +545,24 @@ void ee32_process() Eeprom32_process_state = E32_READSENDING ; } - if ( Eeprom32_process_state == E32_READSENDING ) - { -#if 0 - if ( Spi_complete ) - { - uint32_t blank = 1 ; - x = Eeprom32_data_size + sizeof( struct t_eeprom_header ) ; // Size needing to be checked - p = (uint8_t *) &Eeprom_buffer ; - while ( x ) - { - if ( *p++ != 0xFF ) - { - blank = 0 ; - break ; - } - x -= 1 ; - } - // If not blank, sort erasing here - if ( blank ) - { - Eeprom32_state_after_erase = E32_IDLE ; // TODO really needed? - Eeprom32_process_state = E32_WRITESTART ; - } - else - { -#endif + if (Eeprom32_process_state == E32_READSENDING) { #ifdef SIMU - Eeprom32_process_state = E32_WRITESTART ; + Eeprom32_process_state = E32_WRITESTART ; #else - eeAddress = Eeprom32_address ; - eeprom_write_enable() ; - p = Spi_tx_buf ; - *p = 0x20 ; // Block Erase command - *(p+1) = eeAddress >> 16 ; - *(p+2) = eeAddress >> 8 ; - *(p+3) = eeAddress ; // 3 bytes address - spi_PDC_action( p, 0, 0, 4, 0 ) ; - Eeprom32_process_state = E32_ERASESENDING ; - Eeprom32_state_after_erase = E32_WRITESTART ; + eeAddress = Eeprom32_address ; + eeprom_write_enable() ; + p = Spi_tx_buf ; + *p = 0x20 ; // Block Erase command + *(p+1) = eeAddress >> 16 ; + *(p+2) = eeAddress >> 8 ; + *(p+3) = eeAddress ; // 3 bytes address + spi_PDC_action( p, 0, 0, 4, 0 ) ; + Eeprom32_process_state = E32_ERASESENDING ; + Eeprom32_state_after_erase = E32_WRITESTART ; #endif - // } - // } } - if ( Eeprom32_process_state == E32_WRITESTART ) - { + if (Eeprom32_process_state == E32_WRITESTART) { uint32_t total_size ; p = Eeprom32_source_address; q = (uint8_t *) &Eeprom_buffer.data; diff --git a/radio/src/eeprom_rlc.cpp b/radio/src/eeprom_rlc.cpp index 190dcdbe8..5dc845404 100644 --- a/radio/src/eeprom_rlc.cpp +++ b/radio/src/eeprom_rlc.cpp @@ -746,8 +746,7 @@ void RlcFile::nextRlcWriteStep() if (m_rlc_len==0) goto close; - for (i=1; 1; i++) // !! laeuft ein byte zu weit !! - { + for (i=1; 1; i++) { // !! laeuft ein byte zu weit !! bool cur0 = m_rlc_buf[i] == 0; if (cur0 != run0 || cnt==0x3f || (cnt0 && cnt==0x0f) || i==m_rlc_len) { if (run0) { @@ -782,59 +781,57 @@ void RlcFile::nextRlcWriteStep() close: - switch(m_write_step) { - case WRITE_START_STEP: - { - blkid_t fri=0; + switch(m_write_step) { + case WRITE_START_STEP: { + blkid_t fri = 0; - if (m_currBlk && (fri=EeFsGetLink(m_currBlk))) { - // TODO reuse EeFsFree!!! - blkid_t prev_freeList = eeFs.freeList; - eeFs.freeList = fri; + if (m_currBlk && (fri = EeFsGetLink(m_currBlk))) { + // TODO reuse EeFsFree!!! + blkid_t prev_freeList = eeFs.freeList; + eeFs.freeList = fri; #if defined(PCBTARANIS) - freeBlocks++; + freeBlocks++; #endif - while( EeFsGetLink(fri)) { - fri = EeFsGetLink(fri); + while (EeFsGetLink(fri)) { + fri = EeFsGetLink(fri); #if defined(PCBTARANIS) - freeBlocks++; + freeBlocks++; #endif - } - m_write_step = WRITE_FREE_UNUSED_BLOCKS_STEP1; - EeFsSetLink(fri, prev_freeList); - return; - } - } + } + m_write_step = WRITE_FREE_UNUSED_BLOCKS_STEP1; + EeFsSetLink(fri, prev_freeList); + return; + } + } - case WRITE_FINAL_DIRENT_STEP: - { - m_currBlk = eeFs.files[FILE_TMP].startBlk; - DirEnt & f = eeFs.files[m_fileId]; - eeFs.files[FILE_TMP].startBlk = f.startBlk; - eeFs.files[FILE_TMP].size = f.size; - f.startBlk = m_currBlk; - f.size = m_pos; - f.typ = eeFs.files[FILE_TMP].typ; - m_write_step = WRITE_TMP_DIRENT_STEP; - EeFsFlushDirEnt(m_fileId); - return; - } + case WRITE_FINAL_DIRENT_STEP: { + m_currBlk = eeFs.files[FILE_TMP].startBlk; + DirEnt & f = eeFs.files[m_fileId]; + eeFs.files[FILE_TMP].startBlk = f.startBlk; + eeFs.files[FILE_TMP].size = f.size; + f.startBlk = m_currBlk; + f.size = m_pos; + f.typ = eeFs.files[FILE_TMP].typ; + m_write_step = WRITE_TMP_DIRENT_STEP; + EeFsFlushDirEnt(m_fileId); + return; + } - case WRITE_TMP_DIRENT_STEP: - m_write_step = 0; - EeFsFlushDirEnt(FILE_TMP); - return; + case WRITE_TMP_DIRENT_STEP: + m_write_step = 0; + EeFsFlushDirEnt(FILE_TMP); + return; - case WRITE_FREE_UNUSED_BLOCKS_STEP1: - m_write_step = WRITE_FREE_UNUSED_BLOCKS_STEP2; - EeFsSetLink(m_currBlk, 0); - return; + case WRITE_FREE_UNUSED_BLOCKS_STEP1: + m_write_step = WRITE_FREE_UNUSED_BLOCKS_STEP2; + EeFsSetLink(m_currBlk, 0); + return; - case WRITE_FREE_UNUSED_BLOCKS_STEP2: - m_write_step = WRITE_FINAL_DIRENT_STEP; - EeFsFlushFreelist(); - return; - } + case WRITE_FREE_UNUSED_BLOCKS_STEP2: + m_write_step = WRITE_FINAL_DIRENT_STEP; + EeFsFlushFreelist(); + return; + } } void RlcFile::flush() diff --git a/radio/src/eeprom_rlc.h b/radio/src/eeprom_rlc.h index bec337033..db285a6fe 100644 --- a/radio/src/eeprom_rlc.h +++ b/radio/src/eeprom_rlc.h @@ -161,10 +161,10 @@ inline uint8_t write_errno() { return s_write_err; } class RlcFile: public EFile { - uint8_t m_bRlc; // control byte for run length decoder - uint8_t m_zeroes; + uint8_t m_bRlc; // control byte for run length decoder + uint8_t m_zeroes; - uint8_t m_flags; + uint8_t m_flags; #define WRITE_FIRST_LINK 0x01 #define WRITE_NEXT_LINK_1 0x02 #define WRITE_NEXT_LINK_2 0x03 @@ -173,41 +173,41 @@ class RlcFile: public EFile #define WRITE_FREE_UNUSED_BLOCKS_STEP2 0x30 #define WRITE_FINAL_DIRENT_STEP 0x40 #define WRITE_TMP_DIRENT_STEP 0x50 - uint8_t m_write_step; - uint16_t m_rlc_len; - uint8_t * m_rlc_buf; - uint8_t m_cur_rlc_len; - uint8_t m_write1_byte; - uint8_t m_write_len; - uint8_t * m_write_buf; + uint8_t m_write_step; + uint16_t m_rlc_len; + uint8_t * m_rlc_buf; + uint8_t m_cur_rlc_len; + uint8_t m_write1_byte; + uint8_t m_write_len; + uint8_t * m_write_buf; #if defined (EEPROM_PROGRESS_BAR) - uint8_t m_ratio; + uint8_t m_ratio; #endif -public: + public: - void openRlc(uint8_t i_fileId); + void openRlc(uint8_t i_fileId); - void create(uint8_t i_fileId, uint8_t typ, uint8_t sync_write); + void create(uint8_t i_fileId, uint8_t typ, uint8_t sync_write); - /// copy contents of i_fileSrc to i_fileDst - bool copy(uint8_t i_fileDst, uint8_t i_fileSrc); + /// copy contents of i_fileSrc to i_fileDst + bool copy(uint8_t i_fileDst, uint8_t i_fileSrc); - inline bool isWriting() { return m_write_step != 0; } - void write(uint8_t *buf, uint8_t i_len); - void write1(uint8_t b); - void nextWriteStep(); - void nextRlcWriteStep(); - void writeRlc(uint8_t i_fileId, uint8_t typ, uint8_t *buf, uint16_t i_len, uint8_t sync_write); + inline bool isWriting() { return m_write_step != 0; } + void write(uint8_t *buf, uint8_t i_len); + void write1(uint8_t b); + void nextWriteStep(); + void nextRlcWriteStep(); + void writeRlc(uint8_t i_fileId, uint8_t typ, uint8_t *buf, uint16_t i_len, uint8_t sync_write); - // flush the current write operation if any - void flush(); + // flush the current write operation if any + void flush(); - // read from opened file and decode rlc-coded data - uint16_t readRlc(uint8_t *buf, uint16_t i_len); + // read from opened file and decode rlc-coded data + uint16_t readRlc(uint8_t *buf, uint16_t i_len); #if defined (EEPROM_PROGRESS_BAR) - void DisplayProgressBar(uint8_t x); + void DisplayProgressBar(uint8_t x); #endif }; diff --git a/radio/src/myeeprom.h b/radio/src/myeeprom.h index 11e8ce8a2..3a1604c21 100644 --- a/radio/src/myeeprom.h +++ b/radio/src/myeeprom.h @@ -829,9 +829,9 @@ enum AdjustGvarFunctionParam { #if defined(CPUARM) #if defined(PCBTARANIS) - #define LEN_CFN_NAME 8 + #define LEN_CFN_NAME 8 #else - #define LEN_CFN_NAME 6 + #define LEN_CFN_NAME 6 #endif PACK(typedef struct t_CustomFnData { // Function Switches data int8_t swtch; diff --git a/radio/src/opentx.h b/radio/src/opentx.h index bd3be54c0..4b8da9dbe 100644 --- a/radio/src/opentx.h +++ b/radio/src/opentx.h @@ -585,24 +585,28 @@ extern uint8_t channel_order(uint8_t x); class Key { #define FILTERBITS 4 + #ifdef SIMU -#define FFVAL 1 + #define FFVAL 1 #else -#define FFVAL ((1< 0; } - void pauseEvents() { m_state = KSTATE_PAUSE; m_cnt = 0; } - void killEvents() { m_state = KSTATE_KILLED; } + + private: + uint8_t m_vals; // key debounce? 4 = 40ms + uint8_t m_cnt; + uint8_t m_state; + public: + void input(bool val, EnumKeys enuk); + bool state() { return m_vals > 0; } + void pauseEvents() { m_state = KSTATE_PAUSE; m_cnt = 0; } + void killEvents() { m_state = KSTATE_KILLED; } }; extern Key keys[NUM_KEYS]; diff --git a/radio/src/rtc.cpp b/radio/src/rtc.cpp index 1dad84604..a13d9696e 100644 --- a/radio/src/rtc.cpp +++ b/radio/src/rtc.cpp @@ -51,10 +51,7 @@ extern void rtcdriver_settime(struct gtm * t); implementations (e.g., UNICOS 9.0 on a Cray Y-MP EL) don't shift right in the usual way when A < 0, so SHR falls back on division if ordinary A >> B doesn't seem to be the usual signed shift. */ -#define SHR(a, b) \ - (-1 >> 1 == -1 \ - ? (a) >> (b) \ - : (a) / (1 << (b)) - ((a) % (1 << (b)) < 0)) +#define SHR(a, b) (-1 >> 1 == -1 ? (a) >> (b) : (a) / (1 << (b)) - ((a) % (1 << (b)) < 0)) /* The extra casts in the following macros work around compiler bugs, e.g., in Cray C 5.0.3.0. */ @@ -487,7 +484,7 @@ __mktime_internal (struct gtm *tp, gtime_t gmktime (struct gtm *tp) { - // no time zone stuff. Just do the math ;) + // no time zone stuff. Just do the math ;) static gtime_t localtime_offset; return __mktime_internal (tp, __localtime_r, &localtime_offset); } diff --git a/radio/src/simu.cpp b/radio/src/simu.cpp index a5f74d730..73458e5b0 100644 --- a/radio/src/simu.cpp +++ b/radio/src/simu.cpp @@ -51,23 +51,24 @@ int g_snapshot_idx = 0; class Open9xSim: public FXMainWindow { FXDECLARE(Open9xSim) -public: - Open9xSim(){}; - Open9xSim(FXApp* a); - long onKeypress(FXObject*,FXSelector,void*); - long onTimeout(FXObject*,FXSelector,void*); - void makeSnapshot(const FXDrawable* drawable); - void doEvents(); - void refreshDiplay(); -private: - FXImage *bmp; - FXImageFrame *bmf; - bool firstTime; + public: + Open9xSim(){}; + Open9xSim(FXApp* a); + long onKeypress(FXObject*,FXSelector,void*); + long onTimeout(FXObject*,FXSelector,void*); + void makeSnapshot(const FXDrawable* drawable); + void doEvents(); + void refreshDiplay(); -public: - FXSlider *sliders[8]; - FXKnob *knobs[NUM_POTS]; + private: + FXImage *bmp; + FXImageFrame *bmf; + bool firstTime; + + public: + FXSlider *sliders[8]; + FXKnob *knobs[NUM_POTS]; }; // Message Map FXDEFMAP(Open9xSim) Open9xSimMap[]={ diff --git a/radio/src/templates.h b/radio/src/templates.h index 2ac2cac71..4de55eddf 100644 --- a/radio/src/templates.h +++ b/radio/src/templates.h @@ -53,8 +53,8 @@ * */ -#ifndef TEMPLATES_H -#define TEMPLATES_H +#ifndef TEMPLATES_H_ +#define TEMPLATES_H_ #include diff --git a/radio/src/translations.h b/radio/src/translations.h index 5ca6b4808..2a0343314 100644 --- a/radio/src/translations.h +++ b/radio/src/translations.h @@ -124,12 +124,12 @@ extern const pm_char STR_OPEN9X[]; #define OFS_VTELEMCHNS (OFS_FUNCSOUNDS + sizeof(TR_FUNCSOUNDS)) #if defined(FRSKY) || defined(CPUARM) #if defined(CPUARM) - #define OFS_VTELEMUNIT_IMP (OFS_VTELEMCHNS + sizeof(TR_VTELEMCHNS)) - #define OFS_VTELEMUNIT_NORM (OFS_VTELEMUNIT_IMP + sizeof(TR_VTELEMUNIT_IMP)) - #define OFS_VALARM (OFS_VTELEMUNIT_NORM + sizeof(TR_VTELEMUNIT_NORM)) + #define OFS_VTELEMUNIT_IMP (OFS_VTELEMCHNS + sizeof(TR_VTELEMCHNS)) + #define OFS_VTELEMUNIT_NORM (OFS_VTELEMUNIT_IMP + sizeof(TR_VTELEMUNIT_IMP)) + #define OFS_VALARM (OFS_VTELEMUNIT_NORM + sizeof(TR_VTELEMUNIT_NORM)) #else - #define OFS_VTELEMUNIT (OFS_VTELEMCHNS + sizeof(TR_VTELEMCHNS)) - #define OFS_VALARM (OFS_VTELEMUNIT + sizeof(TR_VTELEMUNIT)) + #define OFS_VTELEMUNIT (OFS_VTELEMCHNS + sizeof(TR_VTELEMCHNS)) + #define OFS_VALARM (OFS_VTELEMUNIT + sizeof(TR_VTELEMUNIT)) #endif #define OFS_VALARMFN (OFS_VALARM + sizeof(TR_VALARM)) #define OFS_VTELPROTO (OFS_VALARMFN + sizeof(TR_VALARMFN)) From d57697460b4d83964436fad862293ebf1ea62049 Mon Sep 17 00:00:00 2001 From: Kjell Kernen Date: Wed, 26 Feb 2014 15:23:23 +0100 Subject: [PATCH 81/89] Cleaned tabs from code. The ones in mainwindow.cpp are mine. The rest come from other contributors. --- companion/src/CMakeLists.txt | 6 +++--- companion/src/appdata.h | 2 +- companion/src/flashinterface.cpp | 2 +- companion/src/flashinterface.h | 2 +- companion/src/logsdialog.cpp | 2 +- companion/src/mainwindow.cpp | 24 ++++++++++++------------ companion/src/splashlabel.h | 4 ++-- companion/src/warnings.h | 4 ++-- 8 files changed, 23 insertions(+), 23 deletions(-) diff --git a/companion/src/CMakeLists.txt b/companion/src/CMakeLists.txt index 5ac12bd16..1db9309bf 100644 --- a/companion/src/CMakeLists.txt +++ b/companion/src/CMakeLists.txt @@ -398,13 +398,13 @@ IF( APPLE ) ADD_CUSTOM_TARGET( addframeworks ALL COMMAND mkdir -p companion.app/Contents/Frameworks COMMAND mkdir -p companion.app/Contents/Resources - COMMAND mkdir -p companion.app/Contents/translations - COMMAND rsync ${PROJECT_SOURCE_DIR}/images/${MACOSX_BUNDLE_ICON_FILE} companion.app/Contents/Resources/${MACOSX_BUNDLE_ICON_FILE} # Copy the icon files + COMMAND mkdir -p companion.app/Contents/translations + COMMAND rsync ${PROJECT_SOURCE_DIR}/images/${MACOSX_BUNDLE_ICON_FILE} companion.app/Contents/Resources/${MACOSX_BUNDLE_ICON_FILE} # Copy the icon files COMMAND rsync ${PROJECT_SOURCE_DIR}/../targets/mac/lib* companion.app/Contents/Frameworks #COMMAND rsync ${PROJECT_SOURCE_DIR}/../targets/mac/libcrypto.1.0.0.dylib companion.app/Contents/Frameworks COMMAND rsync -r --exclude=.svn ${PROJECT_SOURCE_DIR}/../targets/mac/qt_menu.nib companion.app/Contents/Resources/ COMMAND rsync ${PROJECT_BINARY_DIR}/*.qm companion.app/Contents/translations - COMMAND ${QT_BINARY_DIR}/macdeployqt companion.app + COMMAND ${QT_BINARY_DIR}/macdeployqt companion.app WORKING_DIRECTORY ${WORK_DIR} DEPENDS ${PROJECT_NAME} ) diff --git a/companion/src/appdata.h b/companion/src/appdata.h index 479229221..443f6bab2 100644 --- a/companion/src/appdata.h +++ b/companion/src/appdata.h @@ -166,7 +166,7 @@ class Profile: protected CompStoreObj void vBatWarn (const int); Profile(); - Profile& operator=(const Profile&); + Profile& operator=(const Profile&); void remove(); bool existsOnDisk(); void init(int newIndex); diff --git a/companion/src/flashinterface.cpp b/companion/src/flashinterface.cpp index b72c39cbf..0b56cc795 100644 --- a/companion/src/flashinterface.cpp +++ b/companion/src/flashinterface.cpp @@ -52,7 +52,7 @@ FlashInterface::FlashInterface(QString fileName) char * bin_flash = (char *)malloc(MAX_FSIZE); flash_size = file.read(bin_flash, MAX_FSIZE); flash = QByteArray(bin_flash, flash_size); - free(bin_flash); + free(bin_flash); } else { flash = QByteArray(temp, flash_size); diff --git a/companion/src/flashinterface.h b/companion/src/flashinterface.h index 402c2410d..eb1459d85 100644 --- a/companion/src/flashinterface.h +++ b/companion/src/flashinterface.h @@ -92,5 +92,5 @@ private: protected: bool isValidFlag; }; -#endif /* FLASHINTERFACE_H */ +#endif /* FLASHINTERFACE_H */ diff --git a/companion/src/logsdialog.cpp b/companion/src/logsdialog.cpp index f39a41171..7a4b6745b 100644 --- a/companion/src/logsdialog.cpp +++ b/companion/src/logsdialog.cpp @@ -657,7 +657,7 @@ bool logsDialog::cvsFileParse() QString line=buffer.trimmed(); list.clear(); if(line.size()<1){ - list << ""; + list << ""; } else { while (line.size()>pos2 && (pos2 = rx2.indexIn(line, pos2)) != -1) { QString col; diff --git a/companion/src/mainwindow.cpp b/companion/src/mainwindow.cpp index a988870fe..92ec639ae 100644 --- a/companion/src/mainwindow.cpp +++ b/companion/src/mainwindow.cpp @@ -1538,17 +1538,17 @@ MdiChild *MainWindow::createMdiChild() QAction * MainWindow::addAct(QString icon, QString sName, QString lName, QKeySequence::StandardKey shortcut, const char *slot) { - QAction * newAction = new QAction( this ); - if (!icon.isEmpty()) + QAction * newAction = new QAction( this ); + if (!icon.isEmpty()) newAction->setIcon(CompanionIcon(icon)); - if (!sName.isEmpty()) - newAction->setText(sName); - if (!lName.isEmpty()) - newAction->setStatusTip(lName); - if (shortcut != 0) - newAction->setShortcuts(shortcut); + if (!sName.isEmpty()) + newAction->setText(sName); + if (!lName.isEmpty()) + newAction->setStatusTip(lName); + if (shortcut != 0) + newAction->setShortcuts(shortcut); connect(newAction, SIGNAL(triggered()), this, slot); - return newAction; + return newAction; } QAction * MainWindow::addAct(QString icon, QString sName, QString lName, const char *slot) @@ -1627,7 +1627,7 @@ void MainWindow::createActions() simulateAct = addAct("simulate.png", tr("Simulate..."), tr("Simulate current model"), SLOT(simulate())); loadbackupAct = addAct("open.png", tr("Load Backup..."), tr("Load backup from file"), SLOT(loadBackup())); logsAct = addAct("logs.png", tr("View Log File..."), tr("Open and view log file"), SLOT(logFile())); - appPrefsAct = addAct("apppreferences.png",tr("Settings..."), tr("Edit Settings"), SLOT(appPrefs())); + appPrefsAct = addAct("apppreferences.png",tr("Settings..."), tr("Edit Settings"), SLOT(appPrefs())); fwPrefsAct = addAct("fwpreferences.png", tr("Download..."), tr("Download firmware and voice files"), SLOT(fwPrefs())); checkForUpdatesAct = addAct("update.png", tr("Check for Updates..."), tr("Check OpenTX and Companion updates"), SLOT(doUpdates())); changelogAct = addAct("changelog.png", tr("Companion Changes..."), tr("Show Companion change log"), SLOT(changelog())); @@ -1799,7 +1799,7 @@ void MainWindow::createToolBars() recentToolButton->setMenu(createRecentFileMenu()); recentToolButton->setIcon(CompanionIcon("recentdocument.png")); recentToolButton->setToolTip(tr("Recent Models+Settings")); - recentToolButton->setStatusTip(tr("Show recent Models+Settings documents")); + recentToolButton->setStatusTip(tr("Show recent Models+Settings documents")); fileToolBar->addWidget(recentToolButton); fileToolBar->addAction(saveAct); @@ -1814,7 +1814,7 @@ void MainWindow::createToolBars() profileButton->setMenu(createProfilesMenu()); profileButton->setIcon(CompanionIcon("profiles.png")); profileButton->setToolTip(tr("Radio Settings Profile")); - profileButton->setStatusTip(tr("Show a selection list of radio settings profiles")); + profileButton->setStatusTip(tr("Show a selection list of radio settings profiles")); fileToolBar->addWidget(profileButton); fileToolBar->addAction(editSplashAct); diff --git a/companion/src/splashlabel.h b/companion/src/splashlabel.h index a724d2c8c..d82b23e4f 100644 --- a/companion/src/splashlabel.h +++ b/companion/src/splashlabel.h @@ -14,7 +14,7 @@ * */ #ifndef SPLASHLABEL_H -#define SPLASHLABEL_H +#define SPLASHLABEL_H #include #include @@ -77,5 +77,5 @@ signals: private: int index; }; -#endif /* SPLASHLABEL_H */ +#endif /* SPLASHLABEL_H */ diff --git a/companion/src/warnings.h b/companion/src/warnings.h index c8fb4753e..d322e36a5 100644 --- a/companion/src/warnings.h +++ b/companion/src/warnings.h @@ -1,8 +1,8 @@ #ifndef WARNINGS_H -#define WARNINGS_H +#define WARNINGS_H #define WARNING_LEVEL 0 #define WARNING_ID 6 #define WARNING QObject::tr("Thanks all for the donations, kind messages, nice ideas, constructive proposals etc. for the next OpenTX/Companion funding model.\n\nWe are really appreciative for that!\n\nThe OpenTX/Companion Team.") -#endif /* WARNINGS_H */ +#endif /* WARNINGS_H */ From e0548cdfe8200807051bf896229cbf53dcb5ed1b Mon Sep 17 00:00:00 2001 From: bsongis Date: Wed, 26 Feb 2014 15:28:03 +0100 Subject: [PATCH 82/89] cpplint doesn't complain about mainwindow.cpp --- companion/src/mainwindow.cpp | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/companion/src/mainwindow.cpp b/companion/src/mainwindow.cpp index 92ec639ae..1ebbecec6 100644 --- a/companion/src/mainwindow.cpp +++ b/companion/src/mainwindow.cpp @@ -1558,10 +1558,10 @@ QAction * MainWindow::addAct(QString icon, QString sName, QString lName, const c QAction * MainWindow::addAct(QActionGroup *aGroup, QString sName, QString lName, const char *slot) { - QAction *action = addAct("", sName, lName, QKeySequence::UnknownKey, slot); - action->setCheckable(true); - aGroup->addAction(action); - return action; + QAction *action = addAct("", sName, lName, QKeySequence::UnknownKey, slot); + action->setCheckable(true); + aGroup->addAction(action); + return action; } void MainWindow::createActions() @@ -1884,7 +1884,7 @@ void MainWindow::setActiveSubWindow(QWidget *window) } void MainWindow::updateRecentFileActions() - { +{ int i, numRecentFiles; // Hide all document slots @@ -1995,7 +1995,7 @@ for (i=0; i Date: Wed, 26 Feb 2014 15:34:55 +0100 Subject: [PATCH 83/89] Reformatted radio.xsd with VS2010 that has superior functions for auto formatting code. It used to be more or less built out of tab characters, which I am alergic to. --- companion/src/radio.xsd | 1306 ++++++++++++++++++++------------------- 1 file changed, 656 insertions(+), 650 deletions(-) diff --git a/companion/src/radio.xsd b/companion/src/radio.xsd index b3203f138..fca4d96bc 100644 --- a/companion/src/radio.xsd +++ b/companion/src/radio.xsd @@ -1,685 +1,691 @@ - - - Radio data schema for companion9x. - - + + + Radio data schema for companion9x. + + - - - - - - + + + + + + - - - - - + + + + + - - - + + + - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + - - - - - - - - + + + + + + + + - - - - - - + + + + + + - - - - - - + + + + + + - - - - - - + + + + + + - - - - - + + + - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + - - - - - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + - - - - - - - - - - - - - - - - - - - - - - - + + - - - + + - - + + - - - - - + + - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + - - - - - - - - - - - - + + - - - - - + + - - - - - + + From 86c0678273caba4aa160c5b055ec45cbaefdef25 Mon Sep 17 00:00:00 2001 From: bsongis Date: Wed, 26 Feb 2014 16:09:45 +0100 Subject: [PATCH 84/89] cppcheck experiment. A couple of memory leaks fixed --- companion/src/eeprominterface.cpp | 2 +- companion/src/eeprominterface.h | 4 +- .../src/firmwares/er9x/er9xinterface.cpp | 4 +- companion/src/firmwares/er9x/er9xinterface.h | 2 +- .../firmwares/ersky9x/ersky9xinterface.cpp | 4 +- .../src/firmwares/ersky9x/ersky9xinterface.h | 2 +- .../firmwares/gruvin9x/gruvin9xinterface.cpp | 4 +- .../firmwares/gruvin9x/gruvin9xinterface.h | 2 +- .../src/firmwares/opentx/opentxinterface.cpp | 7 ++-- .../src/firmwares/opentx/opentxinterface.h | 2 +- .../src/firmwares/th9x/th9xinterface.cpp | 4 +- companion/src/firmwares/th9x/th9xinterface.h | 2 +- companion/src/mainwindow.cpp | 37 ++++++++----------- 13 files changed, 35 insertions(+), 41 deletions(-) diff --git a/companion/src/eeprominterface.cpp b/companion/src/eeprominterface.cpp index 19185142b..bf1c91cdc 100644 --- a/companion/src/eeprominterface.cpp +++ b/companion/src/eeprominterface.cpp @@ -1050,7 +1050,7 @@ void RegisterFirmwares() RegisterEepromInterfaces(); } -bool LoadEeprom(RadioData &radioData, uint8_t *eeprom, int size) +bool LoadEeprom(RadioData &radioData, const uint8_t *eeprom, const int size) { foreach(EEPROMInterface *eepromInterface, eepromInterfaces) { if (eepromInterface->load(radioData, eeprom, size)) diff --git a/companion/src/eeprominterface.h b/companion/src/eeprominterface.h index e3526d803..a59d276cc 100644 --- a/companion/src/eeprominterface.h +++ b/companion/src/eeprominterface.h @@ -1082,7 +1082,7 @@ class EEPROMInterface inline BoardEnum getBoard() { return board; } - virtual bool load(RadioData &radioData, uint8_t *eeprom, int size) = 0; + virtual bool load(RadioData &radioData, const uint8_t *eeprom, int size) = 0; virtual bool loadBackup(RadioData &radioData, uint8_t *eeprom, int esize, int index) = 0; @@ -1211,7 +1211,7 @@ inline void applyStickModeToModel(ModelData &model, unsigned int mode) void RegisterFirmwares(); bool LoadBackup(RadioData &radioData, uint8_t *eeprom, int esize, int index); -bool LoadEeprom(RadioData &radioData, uint8_t *eeprom, int size); +bool LoadEeprom(RadioData &radioData, const uint8_t *eeprom, int size); bool LoadEepromXml(RadioData &radioData, QDomDocument &doc); struct Option { diff --git a/companion/src/firmwares/er9x/er9xinterface.cpp b/companion/src/firmwares/er9x/er9xinterface.cpp index a45e5088b..af05f58c5 100644 --- a/companion/src/firmwares/er9x/er9xinterface.cpp +++ b/companion/src/firmwares/er9x/er9xinterface.cpp @@ -114,7 +114,7 @@ bool Er9xInterface::loadxml(RadioData &radioData, QDomDocument &doc) return true; } -bool Er9xInterface::load(RadioData &radioData, uint8_t *eeprom, int size) +bool Er9xInterface::load(RadioData &radioData, const uint8_t *eeprom, int size) { std::cout << "trying er9x import... "; @@ -123,7 +123,7 @@ bool Er9xInterface::load(RadioData &radioData, uint8_t *eeprom, int size) return false; } - if (!efile->EeFsOpen(eeprom, size, BOARD_STOCK)) { + if (!efile->EeFsOpen((uint8_t *)eeprom, size, BOARD_STOCK)) { std::cout << "wrong file system\n"; return false; } diff --git a/companion/src/firmwares/er9x/er9xinterface.h b/companion/src/firmwares/er9x/er9xinterface.h index e6d60b6ee..9ea4854be 100644 --- a/companion/src/firmwares/er9x/er9xinterface.h +++ b/companion/src/firmwares/er9x/er9xinterface.h @@ -34,7 +34,7 @@ class Er9xInterface : public EEPROMInterface virtual const int getMaxModels(); - virtual bool load(RadioData &, uint8_t * eeprom, int size); + virtual bool load(RadioData &, const uint8_t * eeprom, int size); virtual bool loadBackup(RadioData &, uint8_t * eeprom, int esize, int index); diff --git a/companion/src/firmwares/ersky9x/ersky9xinterface.cpp b/companion/src/firmwares/ersky9x/ersky9xinterface.cpp index 97ed8fd5b..7ff98b5a1 100644 --- a/companion/src/firmwares/ersky9x/ersky9xinterface.cpp +++ b/companion/src/firmwares/ersky9x/ersky9xinterface.cpp @@ -151,7 +151,7 @@ bool Ersky9xInterface::loadxml(RadioData &radioData, QDomDocument &doc) return true; } -bool Ersky9xInterface::load(RadioData &radioData, uint8_t *eeprom, int size) +bool Ersky9xInterface::load(RadioData &radioData, const uint8_t *eeprom, int size) { std::cout << "trying ersky9x import... "; @@ -160,7 +160,7 @@ bool Ersky9xInterface::load(RadioData &radioData, uint8_t *eeprom, int size) return false; } - if (!efile->EeFsOpen(eeprom, size, BOARD_SKY9X)) { + if (!efile->EeFsOpen((uint8_t *)eeprom, size, BOARD_SKY9X)) { std::cout << "wrong file system\n"; return false; } diff --git a/companion/src/firmwares/ersky9x/ersky9xinterface.h b/companion/src/firmwares/ersky9x/ersky9xinterface.h index 23473eae4..d37151c05 100644 --- a/companion/src/firmwares/ersky9x/ersky9xinterface.h +++ b/companion/src/firmwares/ersky9x/ersky9xinterface.h @@ -34,7 +34,7 @@ class Ersky9xInterface : public EEPROMInterface virtual const int getMaxModels(); - virtual bool load(RadioData &, uint8_t * eeprom, int size); + virtual bool load(RadioData &, const uint8_t * eeprom, int size); virtual bool loadBackup(RadioData &, uint8_t * eeprom, int esize, int index); diff --git a/companion/src/firmwares/gruvin9x/gruvin9xinterface.cpp b/companion/src/firmwares/gruvin9x/gruvin9xinterface.cpp index a7d1d6f1a..7a2ce5f46 100644 --- a/companion/src/firmwares/gruvin9x/gruvin9xinterface.cpp +++ b/companion/src/firmwares/gruvin9x/gruvin9xinterface.cpp @@ -99,7 +99,7 @@ bool Gruvin9xInterface::loadxml(RadioData &radioData, QDomDocument &doc) } -bool Gruvin9xInterface::load(RadioData &radioData, uint8_t *eeprom, int size) +bool Gruvin9xInterface::load(RadioData &radioData, const uint8_t *eeprom, int size) { std::cout << "trying " << getName() << " import... "; @@ -108,7 +108,7 @@ bool Gruvin9xInterface::load(RadioData &radioData, uint8_t *eeprom, int size) return false; } - if (!efile->EeFsOpen(eeprom, size, BOARD_STOCK)) { + if (!efile->EeFsOpen((uint8_t *)eeprom, size, BOARD_STOCK)) { std::cout << "wrong file system\n"; return false; } diff --git a/companion/src/firmwares/gruvin9x/gruvin9xinterface.h b/companion/src/firmwares/gruvin9x/gruvin9xinterface.h index 7da0975e1..2c8a28dc2 100644 --- a/companion/src/firmwares/gruvin9x/gruvin9xinterface.h +++ b/companion/src/firmwares/gruvin9x/gruvin9xinterface.h @@ -35,7 +35,7 @@ class Gruvin9xInterface : public EEPROMInterface virtual const int getMaxModels(); - virtual bool load(RadioData &, uint8_t *eeprom, int size); + virtual bool load(RadioData &, const uint8_t *eeprom, int size); virtual bool loadBackup(RadioData &, uint8_t *eeprom,int esize, int index); diff --git a/companion/src/firmwares/opentx/opentxinterface.cpp b/companion/src/firmwares/opentx/opentxinterface.cpp index 2f4b0409b..bfa13a168 100644 --- a/companion/src/firmwares/opentx/opentxinterface.cpp +++ b/companion/src/firmwares/opentx/opentxinterface.cpp @@ -290,7 +290,7 @@ bool OpenTxInterface::loadxml(RadioData &radioData, QDomDocument &doc) return false; } -bool OpenTxInterface::load(RadioData &radioData, uint8_t *eeprom, int size) +bool OpenTxInterface::load(RadioData &radioData, const uint8_t *eeprom, int size) { std::cout << "trying " << getName() << " import..."; @@ -305,7 +305,8 @@ bool OpenTxInterface::load(RadioData &radioData, uint8_t *eeprom, int size) if (notnull) { std::cout << " wrong size (" << size << ")\n"; return false; - } else { + } + else { QMessageBox::warning(NULL, "companion", QObject::tr("Your radio probably uses a wrong firmware,\n eeprom size is 4096 but only the first 2048 are used")); size=2048; } @@ -315,7 +316,7 @@ bool OpenTxInterface::load(RadioData &radioData, uint8_t *eeprom, int size) } } - if (!efile->EeFsOpen(eeprom, size, board)) { + if (!efile->EeFsOpen((uint8_t *)eeprom, size, board)) { std::cout << " wrong file system\n"; return false; } diff --git a/companion/src/firmwares/opentx/opentxinterface.h b/companion/src/firmwares/opentx/opentxinterface.h index aef381164..809b9f926 100644 --- a/companion/src/firmwares/opentx/opentxinterface.h +++ b/companion/src/firmwares/opentx/opentxinterface.h @@ -37,7 +37,7 @@ class OpenTxInterface : public EEPROMInterface virtual const int getMaxModels(); - virtual bool load(RadioData &, uint8_t *eeprom, int size); + virtual bool load(RadioData &, const uint8_t *eeprom, int size); virtual bool loadBackup(RadioData &, uint8_t *eeprom, int esize, int index); diff --git a/companion/src/firmwares/th9x/th9xinterface.cpp b/companion/src/firmwares/th9x/th9xinterface.cpp index c0f4f7c4e..8e1b50866 100644 --- a/companion/src/firmwares/th9x/th9xinterface.cpp +++ b/companion/src/firmwares/th9x/th9xinterface.cpp @@ -62,7 +62,7 @@ bool Th9xInterface::loadxml(RadioData &radioData, QDomDocument &doc) return false; } -bool Th9xInterface::load(RadioData &radioData, uint8_t *eeprom, int size) +bool Th9xInterface::load(RadioData &radioData, const uint8_t *eeprom, int size) { std::cout << "trying th9x import... "; @@ -71,7 +71,7 @@ bool Th9xInterface::load(RadioData &radioData, uint8_t *eeprom, int size) return false; } - if (!efile->EeFsOpen(eeprom, size, BOARD_STOCK)) { + if (!efile->EeFsOpen((uint8_t *)eeprom, size, BOARD_STOCK)) { std::cout << "wrong file system\n"; return false; } diff --git a/companion/src/firmwares/th9x/th9xinterface.h b/companion/src/firmwares/th9x/th9xinterface.h index 6e0372107..9b63e7695 100644 --- a/companion/src/firmwares/th9x/th9xinterface.h +++ b/companion/src/firmwares/th9x/th9xinterface.h @@ -34,7 +34,7 @@ class Th9xInterface : public EEPROMInterface virtual const int getMaxModels(); - virtual bool load(RadioData &, uint8_t *eeprom, int size); + virtual bool load(RadioData &, const uint8_t *eeprom, int size); virtual bool loadBackup(RadioData &, uint8_t *eeprom, int esize, int index); diff --git a/companion/src/mainwindow.cpp b/companion/src/mainwindow.cpp index 1ebbecec6..ce66bb4bc 100644 --- a/companion/src/mainwindow.cpp +++ b/companion/src/mainwindow.cpp @@ -104,7 +104,7 @@ MainWindow::MainWindow(): setUnifiedTitleAndToolBarOnMac(true); this->setWindowIcon(QIcon(":/icon.png")); - this->setIconSize(QSize(32,32)); + this->setIconSize(QSize(32, 32)); QNetworkProxyFactory::setUseSystemConfiguration(true); setAcceptDrops(true); @@ -468,7 +468,7 @@ void MainWindow::reply1Finished(QNetworkReply * reply) if (OldFwRev == 0) { showcheckForUpdatesResult = false; // update is available - do not show dialog QString rn = GetFirmware(fwToUpdate)->rnurl; - QAbstractButton *rnButton; + QAbstractButton *rnButton = NULL; msgBox.setWindowTitle("Companion"); msgBox.setInformativeText(tr("Firmware %1 does not seem to have ever been downloaded.\nVersion %2 is available.\nDo you want to download it now ?").arg(fwToUpdate).arg(NewFwRev)); QAbstractButton *YesButton = msgBox.addButton(trUtf8("Yes"), QMessageBox::YesRole); @@ -1198,17 +1198,15 @@ bool MainWindow::isValidEEPROM(QString eepromfile) if (!file.open(QIODevice::ReadOnly | QIODevice::Text)) return false; eeprom_size = file.size(); - uint8_t *eeprom = (uint8_t *)malloc(eeprom_size); + QByteArray eeprom(eeprom_size, 0); QTextStream inputStream(&file); - eeprom_size = HexInterface(inputStream).load(eeprom, eeprom_size); + eeprom_size = HexInterface(inputStream).load((uint8_t *)eeprom.data(), eeprom_size); if (!eeprom_size) { - free(eeprom); return false; } file.close(); RadioData * radioData = new RadioData(); - bool result = LoadEeprom(*radioData, eeprom, eeprom_size); - free(eeprom); + bool result = LoadEeprom(*radioData, (uint8_t *)eeprom.data(), eeprom_size); delete radioData; return result; } @@ -1216,17 +1214,14 @@ bool MainWindow::isValidEEPROM(QString eepromfile) if (!file.open(QFile::ReadOnly)) return false; eeprom_size = file.size(); - uint8_t *eeprom = (uint8_t *)malloc(eeprom_size); - memset(eeprom, 0, eeprom_size); - long read = file.read((char*)eeprom, eeprom_size); + QByteArray eeprom(eeprom_size, 0); + long read = file.read(eeprom.data(), eeprom_size); file.close(); if (read != eeprom_size) { - free(eeprom); return false; } RadioData * radioData = new RadioData(); - bool result = LoadEeprom(*radioData, eeprom, eeprom_size); - free(eeprom); + bool result = LoadEeprom(*radioData, (uint8_t *)eeprom.data(), eeprom_size); delete radioData; return result; } @@ -1280,24 +1275,23 @@ bool MainWindow::convertEEPROM(QString backupFile, QString restoreFile, QString if (!file.open(QIODevice::ReadOnly)) return false; - uint8_t *eeprom = (uint8_t *)malloc(eeprom_size); - long result = file.read((char*)eeprom, eeprom_size); + QByteArray eeprom(eeprom_size, 0); + long result = file.read(eeprom.data(), eeprom_size); file.close(); QSharedPointer radioData = QSharedPointer(new RadioData()); - if (!LoadEeprom(*radioData, eeprom, eeprom_size) || !firmware->saveEEPROM(eeprom, *radioData, variant, version)) + if (!LoadEeprom(*radioData, (uint8_t *)eeprom.data(), eeprom_size) || !firmware->saveEEPROM((uint8_t *)eeprom.data(), *radioData, variant, version)) return false; QFile file2(restoreFile); if (!file2.open(QIODevice::WriteOnly)) return false; - result = file2.write((char*)eeprom, eeprom_size); + result = file2.write(eeprom.constData(), eeprom_size); file2.close(); if (result != eeprom_size) return false; - free(eeprom); return true; } @@ -2060,15 +2054,14 @@ int MainWindow::getEpromVersion(QString fileName) QMessageBox::critical(this, tr("Error"),tr("Error opening file %1:\n%2.").arg(fileName).arg(file.errorString())); return -1; } - uint8_t *eeprom = (uint8_t *)malloc(eeprom_size); - memset(eeprom, 0, eeprom_size); - long result = file.read((char*)eeprom, eeprom_size); + QByteArray eeprom(eeprom_size, 0); + long result = file.read(eeprom.data(), eeprom_size); file.close(); if (result != eeprom_size) { QMessageBox::critical(this, tr("Error"),tr("Error reading file %1:\n%2.").arg(fileName).arg(file.errorString())); return -1; } - if (!LoadEeprom(testData, eeprom, eeprom_size)) { + if (!LoadEeprom(testData, (uint8_t *)eeprom.data(), eeprom_size)) { QMessageBox::critical(this, tr("Error"),tr("Invalid binary Models and Settings File %1").arg(fileName)); return -1; } From fdd2e3f4d40b7f04e053cec93801ab3b19b9503a Mon Sep 17 00:00:00 2001 From: bsongis Date: Wed, 26 Feb 2014 21:19:47 +0100 Subject: [PATCH 85/89] Mixer slow bug (source=MAX, switch, slow up, no slow down) --- radio/src/gtests.cpp | 36 +++++++++++++++++++++++++++++++----- radio/src/opentx.cpp | 3 ++- 2 files changed, 33 insertions(+), 6 deletions(-) diff --git a/radio/src/gtests.cpp b/radio/src/gtests.cpp index 5530d21a2..dbb8df463 100644 --- a/radio/src/gtests.cpp +++ b/radio/src/gtests.cpp @@ -91,8 +91,6 @@ TEST(Trims, infiniteChainedTrims) TEST(outdezNAtt, test_unsigned) { - uint16_t altitude = 65530; - uint8_t refBuf[sizeof(displayBuf)]; memset(displayBuf, 0, sizeof(displayBuf)); lcd_putc(0*FWNUM, 0, '6'); @@ -103,12 +101,12 @@ TEST(outdezNAtt, test_unsigned) memcpy(refBuf, displayBuf, sizeof(displayBuf)); memset(displayBuf, 0, sizeof(displayBuf)); - lcd_outdezNAtt(1, 0, altitude, LEFT|UNSIGN); + lcd_outdezNAtt(0, 0, 65530, LEFT|UNSIGN); EXPECT_EQ(memcmp(refBuf, displayBuf, sizeof(displayBuf)), 0) << "Unsigned numbers will be bad displayed"; } -TEST(EEPROM, 1000_random_writes) +TEST(EEPROM, 100_random_writes) { eepromFile = NULL; // in memory RlcFile f; @@ -117,7 +115,7 @@ TEST(EEPROM, 1000_random_writes) EeFsFormat(); - for(int i=0; i<1000; i++) { + for(int i=0; i<100; i++) { int size = rand()%800; for(int j=0; jspeedDown && md->mltpx!=MLTPX_REP) { + if ((md->speedDown || md->speedUp) && md->mltpx!=MLTPX_REP) { if (mixCondition) { v = (md->mltpx == MLTPX_ADD ? 0 : RESX); apply_offset_and_curve = false; @@ -3825,6 +3825,7 @@ void perOut(uint8_t mode, uint8_t tick10ms) //========== SPEED =============== // now its on input side, but without weight compensation. More like other remote controls // lower weight causes slower movement + if (mode <= e_perout_mode_inactive_phase && (md->speedUp || md->speedDown)) { // there are delay values #define DEL_MULT_SHIFT 8 // we recale to a mult 256 higher value for calculation From baffeeb5b00075851cbe9e00665daa2a5ebced62 Mon Sep 17 00:00:00 2001 From: Kjell Kernen Date: Thu, 27 Feb 2014 13:41:29 +0100 Subject: [PATCH 86/89] Taranis splash image changes --- companion/src/images/library/00008.png | Bin 1343 -> 1358 bytes companion/src/images/library/00009.png | Bin 27584 -> 12775 bytes companion/src/images/library/00010.png | Bin 209 -> 10916 bytes companion/src/images/library/00011.png | Bin 209 -> 7407 bytes companion/src/images/library/00012.png | Bin 209 -> 12578 bytes 5 files changed, 0 insertions(+), 0 deletions(-) diff --git a/companion/src/images/library/00008.png b/companion/src/images/library/00008.png index 14b5b77445e9242a3535546e488a6f1d5776d007..6e45e310a4ff420fc799ee8312964ab385a429cb 100644 GIT binary patch delta 1271 zcmVsXYiTwb z30aj&j0-nKTqIR!Y;s)q-u2G8bMKwG_a^V%H*>PN=gj%uJCpO~%>C}nTtNf~0EC)& ztsylcQGdOppjoep0F>tGamC~0+q~6)Ng9kjJ+63M1t}tsO+2nxTxy~y;|F_Ou{btI z#nnxKg2_!VUyqv)oUC1vHt&@1JMg&q#0er^L9+}_kDF_pd}~&Rq);Gcn#avCE{R8Z zCet`L>6uJ9a21!C3~8tF`O@tAS8d_16aXYPh&VooRX@U)Mb-`ER&LR3bmCPmrurV zkXb%PU-fD!`dQm3euy1ICjFD1Ic1mYxXUaj&DxxL%y)OSWf6_DmOkybm`Cl;M`gY}@5CrN70Vyk5?t@X&+HldM*J1?tj{b?WlD2T z%Q~V2{m%SmsY~&=&)OeQOTx`WnkL<2PQ@^;BiPO?H}Fu=53{k^6}uQ>7N<6o6uEIU z)5?d-HljYGY34OWt0G=EnSaj=ZM7Uxp$Ob!PElNzM77c15w8J_-$(S4c}-BeCN`5e z{rRX2av5ux<*9a`(X+@VvDL~}7=J#>5a-WF!Jm(^zhOw}pV_;RnscqHkEDr84xH2HqsoL6{=MgA(a0s{R9>8Pi#e4SSFx|FE;6qA<17>9-%4IDT*Wh)a^U>= hsFL8EKOa>V+#8ainWQAy33mVh002ovPDHLkV1oU(Y##ss delta 1256 zcmVg%VTyvrx1f6;z7gLN|i0Rho@I zh^wMlUAPfZNK|Orz#Aw-aB*eOxH}I;Y?!8mGt1W|ve3#7z_21mm)JlrWj8 zgVVxf>Vazrlc@);5jvAm#_uc*&Ymtf|2QdZCV$f^@r_dplWA?TT;o)rkeQ5XagyBI zr$c8ltrhn;H5rqfa-J&N12-o9AdjDZ06;f}6D41>G`xc+37_9nmKS;L)1fn&qH+sA zBy5M!Vd&eifO$N?9yZvy#;MB;2JMc^mVW%nEKBfhOq-7Vtb7DLcvUb?-OL>on5x?y zmwzoI*o2qNb`aB|=N*{ON{?WmaGaXPGil2vMOh{z=M*ceJFbj8#7<^egstOGv(U@R z?&ABDKI9Uo7Uon&PU8}@96%=kU>D{Z_J6Pm!X?I3K1)0p$#($NSXZVI$deMnqmZt0Y)jA`&$ElU~CZjKt znaa2-g`_Oon;~drhdu!4#BF>W(+4rjDBpsUwpqt3 zPA$x-yu8Ln{1?;BG+nl&$v;ldM1{?q(&eUQpQ1U3ZLTCvHuQz}_S_u2C_VH6z<*n~ zhLslkT3k#WUVY-!p)n_pdoh9g6u`NZH2KGw$)iGed#;MbMAPdUK4-RNxaU|$UYt2R zs@>13s+3)cGy%tQ76BgZllxKC^r+<+z}pu4e*BbDhhLn+qbf<%4BW<2YstS@fjg;* zs*pzsb8?a6Mw(v7o;&ad-mRd9+9Iex^TVLOF+4r4-A z`=XQr@r4OGO`Xl@X;3@hHYZp#g2WyWwlIsUTl^|{4qOlje1#e0;ZtIThd zx($!(to$Z*q%J1%G#wsus)}*##u{chgIk9F9qXIjsfQshaauD;iG`z^RzF3+iNpv7+?y<%REXm+7E<$hElIf0Lu<+0^G zBj5>pNeoyVdlg3RM>*r{zCr-H^)xzE+_oF;;WK8Ll zF~Mhf`r~}#Y?N6632yRm4KiM@=Rg(hGsRa)#HK#MO*~G^cjVOr7fty6sQTcPeD8T( zGzybB)eWb^V@~zNHT=ibqU26+WpJK}5(d;NTtk>lJ#fL_kE#nU`1?_H!Tk?N>yn~9 S#S+&50000YiW diff --git a/companion/src/images/library/00009.png b/companion/src/images/library/00009.png index 8b4ff54278e07a01e716354305042114fda5f926..bf74ff7b5f77ae99ffbb29032d2be11c810a7e21 100644 GIT binary patch literal 12775 zcmX9_2Rzno_g9HhQ3%NjAqgRSl^0l8mQ;Bne4&NJz4hWQXh(l8}{zB-vU2 z@9+ITpO3dv?)&~-*E!#H&Ks(urF?*bk%EMTHB=0O}g$ixD>N2mp&yN|59kWqQ!%pzMoWsy!+SP!o9}TdpQ#y9XI~Nb&QjXbB2@4 zxKR9RF*iX==V}Hq)8q82PhJI!OxxOtRP?P-RW10tTSwUr%hXY=SB*)~UG^9F@bBO8s*5t~PQv-S(E3f7IglgNI##TnhCan|-x zO(3~mHZ4i0!ryI{_E&sk^Wvcjw~hFg?YBFstE;ySN9xDjA2LfR@z6@nt!&SA?kj9% zwIyREf4=KPj9O@*w`7u+msh@B8{>1m69H8zuU_$e7!|Z{Ppp|)5)u)qJ05F#TPahT`Yun8hsltYrX&84NdLQ%Shu!OUV-$sjg+e=GYJ!d! z-8%bU&g=ISLGm@bsHCeuWvK5ZyW>+~?&RdOhwRR;!P4jpnOg20GAsF3wZRdKk_AQ& zYD1`KD1wa2yiY}{kfwAreEGs)Yis);JbeC>x&ZN2U|mmPkZTg8l-@+DPexBCpL)=# zm@!V{<8*J%)b#XNrrhR<;^N}g1hEJ=aSd&4s+L#*y!DmLUrGgq}Oi`RSh_U#iD&JXz9v1Z;!Ha9mNL>Q?< z>y#<7aI){q%8cK8otT}S#U~s0E(=vk-&n8Omb!7{MwULWl9Cbw6I0#XO1eI;DkpW| z>1RUE706f<^aNtm=F?d>@3C(E36WlC6(01R$+fYy?dt1OR#)H0t(Exf`E$~6rP{hW zQnd`~l7Y6t!9<_N4rTsCD%@ySm##Dm6>rS_s3>a2qeqPkZT4nrr*K88j4b&^woEt_ zo4j=$YQBoMB<=Fw{n>VGx z!^5+Bo!*$7(#w84HRXs4Wng7hW{ ze#lFbx#1!6F3W`?PvP6WOWh41dD|39G#p+H)MMdYqcab_g3I+yrLUH>;73A?7--_h=F#00f7P`Ws zqKH7K55R6oFukIQIMf-)Xi;ksqeB-oKdBpL`+N! zZsAy@%Dsm1I_uNyk$X_U-@cjuem}$ikX4R<=b7+=g43>5o8I`-!;Ze+UNCq^x;i$^kvve+cNcJx_pZutDXyH>Jv z)9u~++D~i)99&Bhh`VQGY;14m5)g>65mFUlROF4JrVQB|Qp-b2@j!_qJw09Dz+lX~ zEG{Xje$?&Hm&*~hJ9+O!h~cq>;vO_Nt8J~NY{$8YKj?L`9j^4pWyU8Y#K{H9c6WC_ zj)`%ft5`|HHS^G>>32Jb*x1`&K+DzBTli7lI2f)pzvkDPBA0^m_~yT2W?jILt$*K$ zkE_s(hjwhffwf`QnjE8p{kuc1lizO6+1A|NT{k{YHJeJ{$+qNUwd43P zL-QL!DI4Fpzc`EHvjHZGO*A>FkFi9IFZnt;I6SMYWQlH4xN$?mB$qBo{v2=2hw=H& zfq@pWsx?h>->Kt0PQ{H{+A>SDwY9b1fBg6~IQT#-ljGo?M=G4S2{a}yDf`u{I@b~! z$`A?ve{UL%aO8{2%hcgYy4m`1`(tVvSPvXHu<9p^N-{P!e*E}xzC#x~kf_G;5kSY= zTNG`Gy5yv`va=(rFxS@7qC|ntye@l)bNu@Cs}2t>$(LF0C#Nn2cR6sP5K+w{jJuy@ zW!*c=cJ|!49lgE1xR$6UPOZ%7z>S8$?`xAO_TJu4jQBq86DY4fRWkS?O)-o(m4=jw zoV+~yfwwLj|N5%zwzoD(etoM*uoP4=Ha;@%!-T^@d$_o`jBUrZOyETUeR|pYi;82% zwyP$L<0Yv=YE?L?=dYoaGW43Fj;r6DmSH{{6cp5GBZS6?kp8=8A3gs@(aLrWwIEo? z&)KNbN4gzAaAPv*`XAqlyYk1%%?0d=j33_`b$j~a1(&nv(Tt1?TsLcmUZ^QQcbtZh zpkVdSpFBlHMJRn-zHbFfxYBt?#}mhoAOE@JixLGqr7K6E{M<`TY3b>s)iNHnOzb~! zVAM_gu2ZdzkUKE?_4{dFE-o&&vZ0>d-c)_wAU)YQ4LcO+_U13zJ)}<)5-wX?-$un9 zDjCp}X2JUw`pjGZ=t$}K^@|Tj5!+Ia$Mc!VEqR)lSU0(_!`}X4sKU-9EoB#%Q)0t@ z!a{Kxi{`?@!mVv>r=_L&3IWenuCA2$s248K0P=9-T-@BKv9qZPTrFzPvX2bR&I}^8y(*=@%~zVL%1P=)!x$bzup|f z3r0qb-@kLBw<04C{rmTiM?j!q)NRD0)WOyDp?8%vab%j)!ZN0ongivdGO9R8==r%Cq@2Pn*C&WxSqZ~VL`#O;!Gc%MLB??_162T zsPI?9J7Ssyw-NKE=HK$iigz-2nMQWGB zU9(yTk+i-U+%zZk-WM-k5Xu9DT0P-0y0Tti#79d<_qUNFLdVERg+20FULIAD{4Kp~ zg;br9m384AODp$mgqnJKXd`5n87wxZ4N)7bDxX8D?gGqgq*v$8TdKAw?4?&@k1fRjSHE*+l{n?4O! zbm$#&s;HQlAbsBBkt%@GAYW;jH!*4%_$PRaRGmHeSh%b>jWm5;#Yf)))@Re0yu_Ij z#ocd%-==3~jNdpMs;H=7lJHRA;k6Mu5<sx`^Se_g1fXqTc*}A$uv`@Z42HoY^ArsPOM^k$-y{i$b z#~>%Bv{VAu(d9r}YO1BGx)%)vc7y~$XP#D$U^&hbaaoYz-Oscz2M33PqHA6^AP*oa zQ7+wU~Pc0PEId$Usq@6Sw1>YCuHFs(wzVsfc~ysyKYaZlM7b&^gQNK?B0>M zH>>IbgysA9?|pv6+5eoH8V#a1ubx@@)ZKjtN-oCGe6+=4OUNX5S%7!fr<$ID0d=St z5cv1+-#dGI>swo)BW|NShvypXivB0I@D!;^V0N!-*CJzLj`th_Uze9lQ&3Q#?Bp3A zzpd_QYwH4e0KpmdkFBf|aOeYdfLfAIh^1V8b6PN0r_ZSvLWz%VAG#H?`2PL-fT`N? zc^w^{YHqnT)r|l-mI(69?oflA!>&U{e8K3CT!Zn2HBwvFhz6pt z#KY6G%c5K zx@N+o>(eKBwu5Xe5n)!Y@x9$n#nwiNF)@nlk!NuUPXuHZAOUJe-JTibbUBE$wzfh{ ze|hVY&`I_ps8A{WP?A=|w~CwiE6|ROP~0k;O6-%k|NcoSy1Meue9j%G3S8X<%pxl- zEtURLz3Y{EMLb|Q8r;Q6eaN{#1fQVb>aeT^7Y)=6%)q6q74;}F#_-^#CRI`AFV!7^ zTb?g6Ga;$ay?99XvLTd=u7yQMoUpwLSM-Ai4^T*d);EC%U42j6>|VZn=_bzfeR487 zCZ@j7w&iJZvYoZ{&QOI92gC;1?!Nl(kJye6T&&=IkMDbc?YO&EJ7MoKGtz{CSta(! z5%02j-wN2DA3uIPjf<P7nha}QHD&-%v>J- z7!I8Pt_?BIBd>N4!H?&gum=r*ZM(;qmeDM9FIuDIFmuxi7M^eu7jNd^Y{9oSZ0dez<7ZFLs9g zg*Hvplq}MXnX*eK;CHgKvyU-`Lu9osE{Y7VeiVaioXD}*_J67cXS4BB zS?&WQS42a9sV6tLb}}bpIDqKg^vj$t`BuAT`to2e4pIblIu(Cty*})}GG8wcpetzS zXj}VxsBEqMdgXa(mduh8L!PF~1q_fA@83%fx{85^m?XVaNV~|}f*q}QwhyT#fHxS! z0T%FWU{B&4L8iDqz@vty=3YtD%YMFo*{&Rd6F}zs==h!$6H1ZD_yz&ojV6yEW5hx&grY9Qz86A!p|cE+$fpEtJmkMI`9<%0E|(y5=|(bcyj4W z*>!=Tp&^Jm^bM@{WNHWtHJ>SHfG#X(dD(m9mr`HZTxG)W)^Z83Hy{2P>W?v8DXYZ7 zXLPp+C0nxm#-me1$1Lo8I-T*9npXUdd0E6=v_o!jI5X#b9C3 z8f?YNpl8IM7m&4cf!jAlUA`)S?BBeh%{2(q;A$c58K#hR7EIV$>2lD2e7UWy4KIVH zt47TqVPb+9=+2ZrTSir^?u=6p7 zgK193X~4!>nUxsvX=rG$#kMrT*TLXY1i|2fYd?Pch{HpPTgjSM_?~I9iPGVzLng4N zQ6wi*pSKi7~yd4bGOxVpNBM%|2f284H9+cB2zs(K(u-nqXp=#pz` z(5Xvr1w}CFk zxfxWK{{DUZT);}%Mz`E1jc9_V%||0XB~8t6pA>_fi&^_fZr89O3xL26{WRt0?UAjo z=IZ)-&zM(4wCGW#bX^qlsZ*!$u!yz5fdBsap1U6SNK%_CT0~4NOeilk^;Tu2EK&{R zCGt(Kf(&<;1;oT+71+-yE0d>e{<7ckrO2KtLiQgI%wSPJpOD9U+8EcbZyYcDI8^bc zxr}No&vD_qN9mXTM=THM=;(+<0tI4{`$XGsj0W;)XG8g49;g01~zQ-1cL zpdnjORj(_SO^B@GSaj1LAL&7;kK4B%t7Wi11vQ7!3$)v0Rn?QM=kq;L%UJzDUs;_V zA=})ZBvmjliyt<*bg94i3Oz9R^JfFZEXog=YMezEV)Fcgpwc1@E&LBdyg^H!IdcYf zY++-eBN}YbSGjy9U}K!svw`_~=hv^iLOtY1N<^l>iZI53?n&;9IR?4by)Q4qn{SQF zZSATW7Wkn6>lM*({_C%Lk(1#N(Jgx}C)Hbz{+r1oh!(L68I*I&1fg=#IMdV9 zKWApr)6#AO^DkIf2>2er{c}o89m|nVWn&D#FZ-ibv|`IK7zrNo6F8&$9g`dk`-Om> z_YRZ|@q4S_o-_~_zI3Gi=v186J%zi`(9#-n6Yq2o@sVahaY1OV3xhm*oJ0`1X-jo|FL7KiI9_R_86wJ%UCq%rLwlRmM6V{ngV@6 z;kYgJ8WM6QFJS3pd!oc00MYlR=<>B62~gC)vbzw#*Q?f<5zw#z3h-pY;^K|KuKEoJ zSOD=WKZO(8kbENOgr`aqJHo)QDnL&2pM0w2(sVEG{Sd??%of;R>_l|8r-IDik8bdz3u;og=DX6*#V|9Cp`GxLZO)V{C znZ`wS2Zpz|Rsfk0XvE(@GJ=ItQ;#8qsDqv*(&>{1uSOc=woYS=!Gv^2nKvdXDM=I1 znXiMR(VuG|@q%`OhCgVpIXSgjl)Y`kXlvCHcjR z7ZIr;@gOEB7<(LN*bnW!C#04bqrkRSZg0*BOG|4Yn=VS(w_{q@F(4YeVUoZ}07!5$8 zyRQsgPw$>0HS_k3D5HP@84AzGZlM#ZlK9eFUfh;95`a**0-N- z9z&Rm_{n1XUteHBikh&y#agprV^dRVe*PmA;lB5mK!Zj`_n-$E_ES&{&3bc0H$jD> zaM1F>TAArEwqOieO2-5xIH4TFycY!px<>LC0}Od0C|<7(+DE@-9E9jVXveij&Lx4~%uoFgs5bTOj$q=eDpl)sf64lpOHSkxsz86>livHuB%o-8U-C0Vy?> z2h+QFwEXDk={aIspn)(YfYqvV-G^^`C!|Pt2IJ@h1!G7ajr!!C+edagAK`)>`1?`@mo;pH9fd2C1pD+2r?;GVBye|9w-cuxCsw#6= zZbd~B&RQ2e&O@$4W!E8k)#u$kvDJB=N>^Whak5w8hkJz};hk6lH{226wtvpO zM6}q)sqV}*&~1BDG#+$1rWoyqqPSb0xE|Xw-AJf(CT*0h(w%mwtgXO zE$o~?)rOGN_21H&RG(&+FcCv?=T>UUe%{;5%Wd_K72;F@e!3UEQ;1(I1sm~<{cl~4 zV!p{F7huYF<;W2@_A?V6r3Y7#HU<0~izi5V9wGQ?LBaoq=j?54?xLUJv&pGgo);C- zVAyr#O3u%e*QGxgL5@u&l}o2k=2!Y&XA~F5WG4GkATB_d)0%L#5(B`A%Jtvl*_p{7 zCOjfzV;g`6;y3J_er{Iu~pq6X1UyA`O#N-a(0vv|FLL7p8O#X(B zsp$ig+#eBv8yt`UP`Kyvfg@T;lJ&@k2z}!$N(kw~9%7LIA!qaaBEJmgb5>Tz5V)k- ztM9Y!Htw`5!m%R}5fKp~xmR)P)>)EL({^H#^0oL1GW8K6yd?-0S!t>1Lqy9}+kgLh z5Cfr9=2n}meeYt`xS}Cth_Lt_hTpu>%ps*QcP z(dUTj5jmLOm^l2p{I43mnmv1%kW0?_&)r0b6iV${8+?Gz@Fr*OxJ zIm*jTofS+9tan3FB02J&`_|UjxF=QT9{dADAj8q4mpwe9))poMe`c(KInJ&kA*+E? zZMmQ=Q;$h(>xZCy&@xQYK94GHu2541fwDp09w?BQIa_f-8vy31~uO ztP2R_-5`!W=UH@YZLTAjJfG7`%+|=r$sMm;InNtI{K3xNz8_{AS5!5u?d|Pe5en3Z_)4<`{EbfeQ%9qnxUx$CrsLqph6ag%4RO#r@OsRn6gP|VHorN0 zhQ;^iF>IG80!vZm!NFu-2L_HXGuJza5D6w#z@J@cs4%)yX_=WJfCyus`@~EN;u8;t zcp0*g^sJc~GcX?7#j>a$LH*;{*s$}qmr7i1ot*ARb8A}{o0M*EtxH^+ru|Qx-wYXk zU)9z%Cdv@D6UqL|#&~^VHe+c?5>o5l{x;1`ycI?ULytYC{G?7SjUa;p+#q5w z^0k2U$BfF;(-RS*-la<|NT?C>gF*5UWRZXw)t~TCJ^-J${=?y-{#J}uF%X3ExZPx3(An8py}J7D z=O~nyd0s5mE`XXKE*QzMt*rn+HI#Xb+HsM4Q!AwQH ze*{(Y<^8pjWOvSq%wUR$VL9wCND{b@;I>v%Y^aW~oZ89YH4Io7n3)f&1>@CG`WWXE zs8DG$^(lj>^pb&a^E`X}VR3Qs-UL6+9Z6=5B@%{DU0vtk9WZ{^*ViY~(Ve$QV$FR| zz;?j$EdT1i19>s(*7@a2zJ8os;h@F7+ongA;wVg@$B%;5;SZgVUF8Tru+>vOYD&<7)~5JxCdfvb=t71 z86bIA;ALrPT!-HeVZxN*SyMk@qyo1D$;JJ68W#Ll|F{dzM-UTHL%2)6tCJPe?w3KM^O=ti(ZcVHqJi z`vgv3HYEaJJ$mLPltc2(-&SBVq}*nFS0IMqISRP*p(UUNFhGJ}SIF$vy?F7sQM<_0 zquAIGBx=;5h(;h_kaC9x@niD?GkGjBVVKCY_sNheH;!@6!q_-epO+YiBSc1BV3>|s z>s`Dr7!;XmD%+_;z8DZH)H)ZNgw|UlR0|6`2uljBimHKaKq}{2v19=MZHErPsB`S` z3#IfL2N8BG6`XU(>AjDM8r4@wb%L{yu@QG_V8BJ1rIrzejUNC93?Amh9th_Mw1#pA zd|#XS?7p$;PUQ7qc%-2b2cJ<=QKjqfAn7`v-gR(4St-Ix0=a>QFxv%gqw**wEDFGI zf)wlLZ2q^z(t)R9W@aYzb!N9Jq&&RL#(YFz9X6zhx`fKoUev{ud+ALN~P zH|s0~ErsG5J38p~(!JiQTNpB-HR#8VQ=@0sUhU@vB$L4aBUyzniATj>A2HikSV7`wbrDB|8q!Yp;d?D`zt%ODWuLa4UiZDJUOY5*`PQpJeQouH*4 z96t_`0P_SfZNBr^BETFGRiaq+IGMHISrp0b-5`a$zI20}e#||9v^6#7FwTG|MAqy5 zdr%c)Idtyyv=c2w(9il$|Ek{Pi^=r#&Me7Kyw=M`6MS?n!RiCgsZ)yC`e0;?Z<|Pa zg6Q-qL+%io^0te5h92~oG)u&@NEguro=YH#cLBe>Bym6EHRPIF)_h5OXjm@XC2tr*Vm!OupnktU<9tR&PxH>+Mnl$+=IXu+ZzR^ zy}>k?02lR1!T?&G%j@&())a#uP`GyO3^66nE%`=$GOSzb2d3ayXGGrr|9fC)ZsZ?# zC#Sa7=MYbI_VtAzhAer4*GI>vrLhx44w(vSmTz?`HVGncg5kiaKYe;I(*~flyH-?I z_F=>LC{`Q+K-MCRaZjICTNi-0F_V*C>^zTDbdS*4Tmxd#4xy3Xn^~dG$~4$)BLo`! z($lwc^ZX08v2813MFk5vb%OIC_AIAj!7{sB> zSF9jF&tedR)l@;;8h8$h4MpsUnP{p(&hGl;LkL*U-nA~O-az7 z+vi{pATL%*c4tSuXzIT8(@h-V2TVH_npDtyATxZLBFwH}BI=unv<&~4m<{S=>&x$m zs#Nd&{P`mx7@UfKeJu`)Ica!b^UYMi6+63NtVO{v5<3iOVf@xMHl(W4>A$j?M*??G zdQJu$B=TN#BS?eAe^K{zKbCO-61Z>5kX_g{KvFE>|4&3yQxgDGOU#B!nI)XdxD=|DMPOd`(3uS$1zU$pmr=q zjRu~5z3`uksb;0$|U%$rEmjZk+eqMTWu^S%_Qv^53B>Cv4cC*f+314E6 z{Bbo~!-#7IzPQO7s^IZ(*%eC%2$##XVExd(uoyRB=dpTu_|g@_JoC2Zn3GK%9rnJy zjCiiG`mp*dP^ZNpL{Znlr%gKaJ7rrfpDrIhW%};X?tOImh>x)7r6}+?;2jvzqI#^66q^w4Hg>o>zVZz-ho%CwEPCwhl`ALV zWo`WYn8KAXCAGskA}qr_iTIAm^BH zJ3BiFODvxuzC6+10Cz?)93`Ln4CxUxDO^v)!0ZbI2X5kg`t**)3MQw_0Z+=xAzz#> zVUJ6kiSEHA9$M-?hHh?+ZqHILxhx$XLL}+yKkFl6D4LLBO|IxwOEszna&q$ig3IIx zB&{D7W0k$YlFMKCi;YkL7VsZ3N!+d-9huI_v%^#ai!zr!5GyKxt3K{eyuTJNVmGH5 z+dEFh@yKLxnE24vcbrUIz^=esLQfJ)mss&(-CkA3wU4?nV1nId$HC35oK@MK5QV@M zs&{bE6f1?KJ4UfDd-ZDOix}j#!C!81Rz0P(rEC4}?M!Un%iWLQ zuh_2YopV;OyLRoetuy{eL80Jy`J(e>b57T*&X$}fRZnS~3t!$sLBUC(swk)D_VaIv ztK0p{i*qZnj|6KqB2~wu56P?iKKzzK=!}lsdAZK(nZMt7p7SZXx3k{QQ2YJ$Q9s6= z=|WpoMAqNbYgSR=JsunR$y|JNp`yRk`00rLoOfdX@q`hMhmlLAV;S*73oAa2PUa@Q zE4kVE`78xScjc4b_fJyv%z8|ElswlHV%)lEN8pA4d9Kp_NwEX1>-JNR?)?lHK)*>b)6;waC{zS&Nr{Ao0v9eYUO((Ss+ZPx~ z#cSgAZ1dtie2~)<+Uf1>&9ZHChpi-DB)c`Vap;o0eRxU=59^LCnVFftXFVQk@~frl z&gdjJJ<-p2-9Fm4i*3ginM9fZ`J1}wio!7m@kX7tHI|3^rWYt!SXgKqGj!7{y;CJb zML8EU^fQ!9t{-JvU0rpPX5YMd^B1e!hYc2ZO*%R{d=hE)#&8E$DOSr|19S0Mw;eI{ zywxYOTQ~H$6zODqvplpL9|K=KO!-z#Kix`H{a|0AV}a3~ID^dUk=gY<(+lCX=JQ@M zlX>{&dF>7F-&1V9weCh~sf+{L)z2^W_bDew+`PFC-`B^-=WT9o@A&w=))6JXsL7RI z(+i5-`~4&v#OeR zD>26NJ%0SS*>?Zix1Z_>y*9`+D-mpbd_+M=Nj z;O6G8yd4}C#(U(*u8ePL3JM#Plj$<`)vc}fZP>73apOq1l>CwFIsVZiZiBAU`!=t0C+H$VEKDVEIx*tDOe0*ebb929b z|4z@r(b!uNSX*D8{N%|E^%&u%=H~LR>8I1PvVKKr$@Hei7?%$_Pu0k-MhKpM_NAla zQvfxy+hFwBeCJ_$e$B_GgLTnZi^=8b#(tL~_pySZk9Bo@zAM>lRW~EoZ&s;+T^t`7=vSg1#{~SV9uZYZit2G&Guc{hkq+7D?85qIn&qI_hr~w z@64Irp`nvDHZP?HGG4r(pxnNFC-ss2`?tl^D`8!6L^p2Q)YRRrWn{!k&9vXNHR}R4 z;h#T$D%WxB*`x03D~m^f4ZeQ;`Y$81_z-lvb_I9Zre$Z-lo)HBKFxr~_4t_Uj#S-X zM>)8;Cdd^YddlXtB*8lL@b=qCzPY z9rFJDiK9o4er#;48Fir^X=`b@^}&==RyGlPwB_f|x(XUujqBGBU#h;tB_qR*O^?NI zXlOufn3|eWQBx})nijkMN6+V9PNKu=vU~NNT@??-E=|nMr4w2saP{E{fkwy)p5O?G*X)3LH@T)isj z?(VLUC=*Y`z-M2>=1RL~PkmJ=vx5}t9kyc+Vh>)SXJFX-@_}Yr#mMYby~%2%?Ak)3 z^y+;7+q}F`1+Ie!8Blhs%zFE(LhtN4c>8M0GcnJ9HqTDQDW5yX!r?Q|wKO+=r8z~F z{EGSI%dcI>jq!@R4qGwelg-S{wRCmeRZD$ZR228?mxY?TdaSIk%*nf~bd81Pwe<4x z^3O9fFMoO{w*NxmeH`<5cHN&NdDR~tapJ=!FJAnUfx2+ewnIueY_}3h4O8f*0wYaR zQ%>>NI~OZ%i($R7sfD7qVuRp;OG!O^eW_-vde5XAIcvee!Dvs|;Pz6i+ji^__nNoI zMx)%et+KnD1B!J@+Q&>Pba>un2%`OxH0!9P7ZOdY1IU~J5ul$0cZ z(>(Jxki#eFgQ+Rj69v)0(6GQ`RtWouap%s6M~^}h6FK;`5_m*K!%;VP@7_(hV+Wsz z2u*ft{a}4edU|?Na`LUh!lSooIPO-N$)&X<>1PB71@%<#u`|a(nqOLCpr_~VAWsCx zi;Ig3&kEhZ(#A$HRrg|Edw@C}6VvS`OGUn@i=r%e2I!<%8!EgDC+7{+NCrkmMU;5d zO`}pTa-#S&9=`vUaaM5Oz73pwe7D2HY4N-)EiIqmz`c4UdYA23HOJcgNsGpWQ~13Y z;S1#!IT5k3!T2J>!^5cA+6D${7cQ{j6+aF-Vrx@8&(2Q6xA^(f;OWz+c)m~5(}Vx~ zv9kF5Sdh;W&lzp^bHZ_TC#Qo~K0p32>Jk+h$^FvD!9h$W@!p*~+oaiPaEMoy=A3XU z@PvL8IPqVqxtogG_UI9*BP=|EOUERmpT0Enhb#-b61_t;j-1x)dqDOOc^TVUpg_M+({&tn@L0!h@PxM(7)J$VQ zo2)f|nwA!LDo#Sj*!VLJ0G^^57at!Vo}&VOFf}#xhm8cE=3^E7Vb`u*<=6MHvJU*r zwN_M83a+v_v|Dih{z{7+Iu;fcL&H5g0&g`XpJZTT3&VzC*FyC}2gHu?_CD^~d7atw z-(N0nZoeZ=za}PYIHD2~?iyrTO#f=o)7RHMdv?nSY%I;RC>*0t76;kyZ3(UNYagv1 zbvfw0==}5N&xewB?A>0|+rz@b0E?9Gvew%9E*Tnoj^>UVHKir`{G1z3OMKd7DIg%w z^S3Q$;McDy{6*yB#~PP3L;@D(oR8XWPM5!k+cd*9pP zKYz>?XNIx;U*U{D*nhq}V(-awdA4k4&YZ!)*Ex4i1-p>_-pTn1<80;t`N<7shKoj- z`Ug=*dG1Dd+2V+*rJ9+Vo|yl6!>zm5ep|42%0tzu;nZ{WfHS)3zsJX!C!^I;%kigg zR_hdvlC=dCxAA*xP37{I8U6`mtWfbO`Fc_?A-qptP&r>_b3`B8@KUR6&LP`YNg%UD zX+S;AG@#F3m!iNs@kYWNj^iUsea=UfY`DW>0gueZsYdX}0CkaurrCZRl}azQ@87I) zL#}M2qy!WVkvflG#?No#X^5Zcnzim-d}#7WA+fOr$jvxACO=fE_5u&aSR4O-<<2gIIbB95b}e-^0U6xw+A(Qj@?d_zDE=$1)(Lec1mLi_gZlJSzl-Zm<72}@Ovah#vHSRJ;frbSEk z6naiTKme<>8*N;Jva|EsSCqgxmzVyHVhhK8{;c`e<=F19+YND&)8EdTkhiy=>{B{= z>{#&KyPHkFzdXNfkHnp|_Eo#3bVGOdBf>H2FBQ;}u3k--vX8;SqSISPMn$>*eO=== z@nK8)^XIflw}6@l9bbFS*%lj%jF&D61Caar`kIUHB5z$8MAvb>^#Tt+e-6GEDsJfp zK{O|vKhw{TkEA?%wsl~ykWk33gBG;R%r$3CysM6l7b{%4w0ClHavO)tC)I2s~kBO(`o&LBlI(!p6m*L|3|s-O(_n+pZ+`PPzq!gvh7sg_z2sg`(vE5uwvO$;*pD zx#{cg2hPUUjEIg_^7K45J3A{7twz@Zl&qt#uZ(XCC}VD65&7VOGRh#B#K7PnRsDge z+UHqW)ix5z->mTaDAAJ(Ly4y^TsUQ8vp-EM@fXgJS^a|pAI-&uO-esGH6E`)Pr_-! zu{pz;oY&>C&!Z$^k6p12XM1ar``K(`rHpS=__#?;ST)NNVyu03mYqZ;y#ZOGw1B9!nsBoh4M@G`)$IlhH z9609kms3nEVhg+5jeq}Ketn9qz%c`OAu!;vl!ISw6#oY8^XCPPz*zYwd2c-_FK@ za?Ex6%Ayv~0g(fm0;sctAdw-bZxdKPtG|hPW#@81sHh1|fT|*l`aq{GrjI-I# z-oCy6^VUiz1WlJq+%Fn{oY;X{Bj2M340-DQa#9Y+7gI_s%L zif@3$+DJH|?BJ;pP6LdMRzxrlyZZoLNJt3zRX2QqSLgQQ*x9$7lAP>tY6NAK1J=EK z`7$sM`ea+KHM47%J3lxH4{!&6qE{r^?$hLCcaSdpYD!w#G}xF<{t0{pvbz%#?*Xra z8v}pHEDSLC%oTNCJhXe^U%OpfzQbNXCUflF`_a*pzvAq4jg2++^_dLc*$}4q@uP~& z(%*w!?n7)3L`*aR-$`Rd=>`CC8U0zsu{yCu!sf?&@@TO>r@XwRKYaM$HCe?BsG6*w zu`pt?R);MohyMd$p`0!IyUSGk+8@iB?aG+Y>twWl0%0NN8ohW+l$_lU6q2UQM@!(R6O4odjG+L=C(Ff z506Dx+hVm;`Aq$m*4C523hnQ%U7GBxIwUFSv^aCsArD~G^IKyP1RvHWh`0+yuXcLjmpr~i_3@7`Mg zL?{yZBUwc%T3XC$*)78<85z_!9z0;e!QZ6y22~#X4u~RQB6J=8N=JZ^9CmD9JeR@2 zL5*1PfV0N#0o(UT*yGa?uz|`7!3U@hT7~<{Y%4w?G!Te81#?}VV!OknSa(2H!KN@% zfGV-o8gNY{p9Mu2I~=tUh!y*hoLy#nwpl5jyoSriCAJ+y0AI0LJpJ^6`{km+Z*Nh zG@dbF6gon0PNPgew1CI5zU()!uPquLDdAWFTE8?Zh(s*|E%>~=Fzr5^8WUbWh>i5d zcg=_0XZ|9%Ds&7^UfuxgLHt3o%WZG6a#-KHcH2w+)nV&qnp6gUpRMa*!+$X_*!rA!{ zp~K?hk>JkQ8p_E!v=6ri$e&2pHMKpo8(R)22o!>p_oSqCP!RJS`Zu--Mck*a<8hz{ zi(2kuE;FsTz5V|E`=St7fI21?ya2Bl*x7~0L}Kd2Vl}Wu@HO#xc=-4t(Y?T0K-BKA zh^^0VRR?OIV4v|g9v>h7_U&6jj6raIyt=r7)JRmB0Z2vMva%+$_aUV{|7Nvq^9Hif z+TL8&)6)Y7gzT|DM#Q9gX!_#obCtiY7Z`EBYHVyAg4l$g#=fq`64oDVlvaS&Rkrvo zo8`F2A>cBs3Z%x3_S~CR$qVZVdC73#YY+ed)bYx;^QdNmwBY`SEyDxQ4HT2KCqU*M zP=E<2IDdW@8yg$W*;lJsT1BXs;oxo9`8dQYUnKW64 z-(R>uwiNgCuzknD1JMmVlc7J^bBjj&QuVg2Tem)xa^QvxNLv$0z4USKJ&G@#onehb z6}EYMW6mw$Gl7fYv>gnj;dll%=IoM5~F&WW6(qc~c>AA@*Y0~SN{avkF{ zt;Ekba38`XyFL=C@!D(?VVuLxj$<81@N|{+^uE$=Y_!Tn3%Fa;4^S1#&;*E;(@_@uge?&}Zc&?N?4inxr>j=>UhYhGJKv__Zt`C2ZWd zk#_fPB5&e+Ltr|Lqb6?kRRCf`L#v7Jf%|OW?#ZuTN8m_30J{3w-VRufQ>7=M%Ckry z7rG-PVPGGJ{_59INr2`7NMBwkdI0d&<<`HQAlX0PGS-R4HFP-CuxUILl?xvNh#>0< zItoPu9Ue<}mqYe0s5w4*@$ytXjtSwFP8HiF$)|^kE9LZS8_>z6y8D9UpaL&|A3{Dz z0i1#u1MUw6>I!HDfkAzJW?9B1A&o=HX=z)Mn^aJXta2aiJ$V;C01h`OP;%=?tc>?j z7zKx8V`GV=fGQ=k_0NuisZ{ zX5opyIgPqHI&vtv6@fHRDmK8NkWYG&lyno=8Ssn>y{Pk6TA z;K2Aed)NWrzI`hf8lLsQsRo`wuW1GYiQab>QXD$hhZGT`d|DLxGiP?9ddo}fq@%;* zVDM%I_d@}|x|oW`64fT-8vz;qR19b$Ut3#~TZT#H;^lQ1tlJ5;K}ku;DIh=@Sh4N| zfCPL8Fp-YFY9dY|+4>vTJJ@)}9Q z6hW&;>%oy+URfC)ABS9thNPjPu??^dd*`o9QTP|=hY=4Ss^EE{9is>m&N>7Gh#zrZY@dLQn%EA3hAy;Ohrg?{7|32gL1jDN4`G()^i6}v?cbf6l=hl3~w9o^~I zr(SddsO&qTptjjmn~Osu`3Mi=Gu|ce{UH6(y$*EE)>uS|x8}7ee3Sh2Q;x?I_g3wr zmqn!)Fk^*c(mu*m9F~~aO`A|N=ooCRx|KfoQiK~v`n^_bw$u&EW`B7z{#_rUZWVU>4-f>vT?V5OlzB@#yPA<%N9_1#n(=jjU&0-$s736)%MNw*^+eT2 zIn#(gx)XvdPC-FI0TCX6tCEWo-tNJP;_zJ-gL?-l!f9dZGSDzEryno;DcblsR5N>f z?dSUdH-J5Q0cgmgqFg-g=`qFWCED0n(Kw&9G;3S~AD>*NKK1%DX)P-Pd7PcoiPz{i z`mXe-J^jdG-Ml%rZibkD9~nNq$;(wdt_-Px_;2y+t zG>3y2U)1pUT|9o;^0ULoAP=LyuJ#yU=O`?$u2>td`3_Sop6p&aJ2buMUbOmT(QwWk zzRp!UyDMWI1q6p-7f%MtF5iTk1e9rC)JX~`*w%3vH6U5g83)KG7Z%oZ+pQawq5@)_ z4EYI2pU4w#(twc(kaiE+bxGrkYS)>IW1WHVP^}#Qd=)e^Gqbd{RZi6<9%SQCKXz`1 zbIU0OrYPNX!rJh*bZl&=(4~FnD>zsn@1wJU711*@2SU}G8mPrak4E`H)lr4aTUhuA zHYa4>BZ?&}m-eI-7e9tF0YXH;Aw)7frXI%vsKan(&0e2F!NcEBQr)ZQ<%ALvAkSq+ zqk3L=Qw0hpsuxu&4}{U2D~%x|l7|k7Iu5A7Iaqxb(!a#8oL#zV_inAaB)hEo-pZQE zLYME9bhoe8o1=+dQ&fV2f&{litpRugsD{EkjgtSyd&y-izkdh5HDTA};dK-^-PwIu z&0dH8O(qydnXl~8_#J62q$ojAwdpR6hgZ_v+Bz41k{Cl88h66e(DreDu3B67&y}qm zM^^)|^uv3hwffi#9gEkrEn9JUk&zJ`8k!7p3ab|#4Ud_r?vL!su$J^>CBuG$w?R*z za)X;Hfgxb4!hv$c%CGedtol%I-#!TF!z%0Z7!FWVR~Mlo;Kh)mU%O43;VXf;+%5L* zarysQfV(?@m<0p{>CCelEG~_Al~h(%QogDhnSFzw*VWZUdtyD}=>OyiCk)~P2M!Q_ za*u8P%}m2Q`kgyxZ*Aud3jplIn_^qxqy-cSoDW48#~xB#JOO#mB4-z>S^Xfr<#SY5 zPEN>Zd_68#-l^QPzi*M@;T{#b`Ne-jdX!;2<-zz*OUMkSzlw?P;_rbM#dnj2l<@A z&#}<_E=BP%CO+rqzo5FIj1M>-!D4KLq`LmXQsUYI2mS&y0U%rdT-sL1T1Ga6hMS7A zC`wz1$L25miqjE_CTH%~r(G8tjJ+n63X6(hO*7FJG+FW-K77V<9i*|(L`q0f2!ww2 zEF(jmGmPGjryvrPhd8r1b&mB1@{mEGf@%%zFQ*MA8eHpreeNmGT84vygSn0$k4M!8 zaD;mT8%1%Gn$B2pzx4b+2(IYie(;io0lT)X{f;g}% zi86R|3p)YAkmJBDR5UayO+|zJ<*06hVi8(@p~!`fmi9eFdAK%;Cr|doCdXm?vASY zDdBh=Ug6KkNG+HlG{dPWM}WH%g1(-r1 z0!kyL^gTKe`8ap(q1!kR-1<{d31I5<$xQ-_-@3c+eY1j>vRyUk{(Jf`<%;>qekG6a zx9b4THW_uJO5q8|NnC?5?+DlKoo#0wn`?&{j}OFaC>%~b@7EzCVtMV_Ao?$G$1A&T z8Gv|;oP{;I8l2?t>S|>!lkvZQ2Y{2Xtwced;FrNP=GwPUJ%3N+4lUh-FsGV+{uDA} z$ZJ2Pth^ci0rO)`TiYxOspggzRV}R{=Cb)sH%#YK87`LlQ~5girJ-mJ%)%dE9a}%+ zQF4d%$W*r@hcN;UT-jF|6ILX(CPw7KQD#XDLQQQeVi3}6%hSZs09gX#I)&N`guDFb zY+1SGAxHQTt0#p?s_E9PTQ;4A(I}x)aox+e(PXEAaUeTTqSX-%1Wf^yjtE9zW_cZs zq1q*Dd&7GmNfYN=mV&r<^HA{IXPQn%)S4416(^EO#P|*rSiIFlj~sReu*nl3d{96b zL|-;0Krlu_A=(Ut!G%8=+4e`{iT!hIEdLhjJHXNruX$0L<1@4?D=Ubc+(UB5Hotc> za6ht3Hf?VL0IOhnpL=UbN5J|CLO8ji%sX#46JA#!6xDHEl8z>$6oo&gizT6uV z8bxfe*OpD(D1fipY`n0krDwmMCglks4q^#c^qv@VK6=DwSqfP$tSB^fc;@}sD}e2R zfF)hNYuBx7T^@=olQMR68qMHwk&oEb z>uxMF%H=p;5Y(SfU!E?@jYzp4jrTykL-E0qfjJSa1qTWI3!wv22mpxsN&Y82En%_t zQV=|-=qm~Cx1o;zYKS|D)DZ|b5C%OgbNQs6)ur(ogalv*tEy4~>iD{TswgkN&6?88 z3Yi5z#K(95ay7OmWd<`NW95(6m#VI2f3rgP3har>-~?ZknDzJlV2Mx=;FH1ohj8!< z%?DM8=z@!9O-veL_du%qjdd8!~7&`}G5u^s< zPW^C88mhr%#1WqAzYn6@%L4Bs{HCV5I%&#i!WI_KC>Kfp0oK93h|nJS-rAaTtzF`d zaz8EmpRxd-6}_NlS{#2|s|-hu9I^TNHWzC{s_$TMo`$+Q!)|RV0mq~9ej<;h-Nm7}{QBLLyuLi9&w+{)ePZD5v9TVM z-4jXL;W07%<|j!&h2(vx5`oSL)`E$W7-Q@a3^H%uel2gi;2^}BIzzh>B~W1UdZ;-_ zXHZe7@I_JC>NI<+sm1UoxcM2{76gE41HkHlGK{o=lZO7JMv*`xAQcS>I)lsy>8I1M zHL4-=G>ml?wE;vT9W#V7hhv1jj{OKgl7OEwlZZP4dy>O@CW1B{G7WpQS^ypoGcU-vwaa7VKuBol0zoI=vo7pYe7t7&7X5JtyY$EDM%l)^ zZXc2<0$i#YcBW@x`3P1`j=({SPb_9POS^gOuu~w=DE0M1Nb&FBKXmARqs-DB=-vPZ zzyTnB5p1mZ@W6h=lY*spXOHBL5@RG1FQZ*{*jJEvAi*v8yqaEK#k3oJfxzVXrJ!`< z7UlwBo<|0up7^w4$M!QMtb5s zZL3P%^WxG+pM2j0`TiaE-4?cJXD2jlOcEI|ME9M|nt;{x#;j^9p1r!a_sSao9vR4^ zWM{zE3Xh8m1>DAZ?LYr!faC5^x5rwVbNw2f!F*%K(D>{mX+}_b$jAKpRS%qD7Yoai zckdps9dm)CbhmxfqPx@^pBI{kl<%rEWD;(gKPV}L=OQ115`>HZ50(s%jBpp1u?|>9 zM?oJ2ki}VfSnh1Olsy7bLgXDBjWv^OUJ1@cQ!%_7358Bueh4aHW=P{; z-K20RN!Cz7O-40Ntxt8elPY4fn%a(OkCI|QRT6d5)s@%Li3lH4$*Sq@f9GR0^%nXZ zv_O=fBlbNMF#iV;$%IHPN`&0ck89zKPI#0&U4FPR@E#Io&@dws5`_Cst9tE1U@=8C zibNg&-@*3~;#7hxgTf1sH3|<=Gc7qY^OUrcnHe{TJv1y30VL>X@G-fs>PEIMAHP3d z)3u}}`Q2B|$E1wO=kHGlkmj|KynvIi;6&~-MV@>OJORh@T&~ql1Xtix!zD-D4Y@_` znEC>j(cRb^q!ge@CTaV^Jps_;=jB!6jIV<%CTAJjU_p8ls`361Ct``h@!`_qfI4ZL zXIQxj@&f@{$RNwC&R>EpRatm_^R2D)?@&j2eF1E`~eA*7{%zp*56+e zRQcZW&=eYEj`OfCJZxkS_QJmgp^5EY8FMAcwW}?B@b5PA{{VA=VSw5PoE4N(sT9gY zawj@FY#I}en>l0}iFCQOSY>oagE23e5vId#@@Bipt2m#W7&WSCI z#sk6<5ZN{8NXN{Kwi)yB!PwXs6Qz@j%e$U!)YR0$AtBrc4vcbm2+?n!UTGMbUO)t* z!)v;Mls=O4FfzJ>u6D`S`(>JL`uyTZc0heT(yxGkOrc6oI-nNuzDJ`%7pQ5ZFQr8mz|nXEGe!79 zp(4a;Bu$q8<&}|?3_N^L90Wn&A?5jRKaP45JV9Rd2k0DgChdB}f(R+QI(hFgP#N4K|2VtS^NgE@fBz;l z#&fJ75a*3+t{c>oWC&C>G|cD5I*BrYWe#rn2SEfXa8TuYRGKf%&D>0*W$io{-=Eex zu7sn23S*8QNy4WPsYAVoWkL($QtK8RDp)du6%~fCc?AvU~Mk z-p0+F9ec|+K^7nn2WsatL@{5!e95I`zj`L~39{skjdm(mZ=n(B*b~Te>%$G*bVeoB zdZ=v&uk1+l{EuZUBzY@(pJZlkhl&E*m?V#ZUY2iOj%2Tcmg&U=aCPw_sOoVQC9~Bo3SxEt{UJsS z4zv>*nR!l#4WU)#5OAA&rVSFh43$(@BDU{pz(*z&vsaQnFukK7ZhV2h%=!{m+k zrpBxt+Y-iObvHD0@4kJZ&@)3kV7f)4=SC(Ze8v(5h`u)$N05dHpO_Bt4-90Wr9FYn z2TW%Y%S0;V!2v^M1R@b*LCu2QjXwTXdtUw9-7IG7dUNr+tVjHikDzDMyKo__evq4o zXJE@@tdTH3ej8R7095P|r)M8&=N7zR*5C(li~i@kp7RK z=ZX3XEfP*k5>!HPVtk-Y%>TSKhtuBb;<#}O2&kOsZ;fd#EG_7?1+Up8e|?3g4B-hv zVgT8v5T}Fdu&>TnHGOKNHM_=KJovtEu#>fojd{~kB@CgIF8j_T?xrv~l zAWjG+aGLN3LfB!dUjjVAjturnM}{d1;qnir^K!LAcuyi__c9G3fB=z?YhraS$rnxv z+Ch=aC}Q6Z5FFlkEjR+)!SW_4>is6Ak8#2^>}qNhhDiI6 zTNKU8LoE!X}U=b|w@e!>XJYFEKXqGzJAcFKIBUIWMo$PUDtpuA*9)~zY9ZmGZK#J zIqtKz)J>C~N(a=9;RWD7qHvn^yGyeZn{IU~rfgfmyA=2RA|gWww4}Xz$3y`|&)2ss zd~^CYD};^+Uqyg}6j1I?xt|oUk-b(IhVF348t1q8iewIQRE0Hj=_5^OX7==>Q7Nhg zs^-b$CWvtGe`$GndErvMM(@;_>$E(itFM0>qBERAWGs@d5JRiGI}s8YUCaHL82G&) zS%_R2-q;=~j%2FnwV#K8Ct$R?mS)UO?0tKq({`w2uImyW#?uaYD5R2|&J0?|XBi0u z?kv2H=sjCZeHAiAANudfY68zfEbH(X$>jbujZrDVnEyNt0PKF8BhX1qy`0AY2W;8B z0s=v3c!**Y3?+Cz1m7VkDx4S4lpS&}prI)4>cD~D&r~1&Ax5)>Ms_(IezJa+kzjLg zSy_H|%$rYflJ}tdpn8D=BB_YhcpNcFus$;7LbMlfJ2J3?owxWq8DjAS0CKQLo9+X9 z3}2vS$_`un86NHh76pYtv>8 z0hX}panrK_@#{-us0f|r|;12x{Emq^mOfW=LFtrQ2^VnKOd1I*h*6h_zQ2A z=!|F1@ES!DG^Y^RnbjJylZgq~70;euMkWDNAjnS~=5xDkQ5alic=jJZeq>o60Ug2~ z^h{=XLIL6@oC|#K$0%7k)qm5hB;vLg7zuB^tul%{g(={l^wQrP0)tWI?}5(CU`EKc zV2~-xsDL}=pl)VqS@aJU*xezLYUxbiZ5SmY(N@&O=L!g5Qb;)tP-f_7_SNzy!ndZ! zFb_7&#D%Kl4O?~u`4{?DjTWu89tCKGh=jn`j@OLnX9P_H@sPd^RcV)`E$i#ouZegB zM6L0)bI%b+9)u>IJ&Zx!#88)j&mDQSvIvTJ6y=By#}MyUPTsXXNAV|TyyR58=N+o{B zjvW?gYZN4Ow#IlwQdIN?Ch)*XNURWt4#lyuaZu&;$GNIk`Wa{RXm{glA|%QSuP)`D zI&a7to8(Z90d!>u#1Qv^NW}+otXs1jFgUl;S!QQt)t6N?w%F7-H`-oP>b>MMGks5H zF$n+s-ZEZBf`s@-)~yUs6CxOqxB-Z;M*(w})w2@hlV}HPQog#?u4jj;jDAUm`2Y!^ zSD-dPm_jI>yA$j)0MGt5_!=D}qkokdNoIi@IQ;v2zWN@A7DW2+hpm=}$VvnC3+y`J zEj+w8=gpgZ6sOhR-BI7u^sW)k`t|EqAZU`92c-T00Uc%6YyQ>z#V|M$aK<*4Gs7nU zw02DIdv1`)hfWH|2dXW}i6Xaxy@ipvaIsN>cJ81pL%>z!9dbP z3zx9%P%$-qq7rfqAqE7Y0J`Cg+9bzgA8ToCZ8fIk5S41=ERU}O(S zNdtyNAz&`cpEw<=wWe>xJy-|lfBN&WaeHXe1naLWQj2{anYu{wvW3_8;gmkj$vJ(W zKO-aK5`y~3R$wHOTk~Dw(<7`qbUqGvjHKuZ0e&sWiLLosd?+*$MxM<7#o}TkqVNc> zDm1_CE$VoVRx`PGee-RE>=)M6@v?1%fB1WL(N}#1gRYSCQ?s+Ro?OFUVki*Sw;ZF=U{CLbF+d9 z*NGdPO5sA>Pq=&53x_bbbJx*b-dW}O+CIkffVJU?_jf5n-uu1PmJig{<)jK8J|0zT z&R1(LKDcmeX^EYiv!}ny^YgS<<0LDC1z%bBa_Qjdt}2V1*Ve7VV5sn$Ae71Z%}!5O zoDz;{$u^OdS5Sa|teCE+3u0@K`3tfZp=B64MMHOoyBtv2YDe{AS?AK1CvwESg58Ta zMZn|9ec8p_AFU(nuEP67@QK6`G#*RQ1;~E@0}v1qVeWzm84RK8qV2zv%}05jT6lYx zJeLMgc3I!Qz_w2JV=#6~ntK{PZV zCclZf5iGtuK)gs^f-Kja@6K=NUHU?EYr zBch`APQ8JqdK1!a6uKVZ5k#OHw6vKoUozg^<@@!va8xar5Zdk*Os4#AHdr)SD^Z3_ zUMS}3J*|LOs{E>(%{od*xz#iUIj$l|MMq;?%lfrcMSbF zR5#bTa8-w&1pA<6$V;3mTqSz6bnj?ib5=tzoHO`V;2S{*>M3W+O9x4L~>7(P30f>#kDZBT%AA@)c z{D2@`&406UwdmMnMhz65Ol6|NBHG?$d5GBZ2!?LkTybs4!&Mv>x9sZtUTD{53sZw+ zUI+0Bxj0#;Uw6LTYOJrngpLEH2i`9Z$fGZhWA-s_#W>M`x3nz_iHYBGNT9ReHWJpeGmiA>2&AF&b7m3kFe z&K!x?1oIL+aDW$22U`*h9XN&AvWIvmpq;XBw_MI?BU%Wf{SAzoK54S__i;nbg*uDL z5i+bgS%}#JO#V8ERCNnDVx<23_2Y$TvAnT#4j`~+Je=}x#M0n@z~Tsx~EcoAZa65vOTDhV@S5IB<5O0a=R zRPyeB!47G>(`ZK*E4Pydiyy@i+R6QZ0`HW4P8$jopw|R^#LxiFYuj`M4R@1i6y%M; z4CNns0v7o~EIyuJR5V@5pf%H+5r@75f1+%#n!nA_VE=;=$2aZnGEgGnF(Q>phGNU;<#? z5>q#T78M!Ur63d3h|v;Au+)gbg)iT}Rlz-V8_CSW=((?D`tr|LC!1Abl#x@!PAg%G z(v!+}QMqGzm88AToVng9PbSYuCLDB7?=6B(=gWMK(3LW^|t^yLJ5f{a3j z7;VpULJZ-)8gFT7DIDRTttNP$LeYN;xf?jv?TxzcmuqkU)EBIb7{$Ml|-xu_Wf{so(RTUNHb<*+x{Mf;&x(U;*+tpjPPGV z(J#)Pp4Ok6@{GEQ>fyJE`bUv#_V3lSXV3mEc97c$pvOiSc7C?tEC}eJTb@jfw z$3L_ez`ic8=~Lu@VOY(7!MV(5#a|;YFfi~&7!-Nvr||d4D30{>r-Kmnfs0g6o!WU$ zPEu0Rp_~3%SAG46>xH?nX6h2-M%eract3mcE!*g+z0wD8TJvKPhULqo0V$Cl@2lXQ@6sN|Z4raz0n~&E!~c4$nPx8;VdI2!2cpkNHTRsv4F7Vg z?+P>8#b~ONiILH#V)tpqM4iI3wNl3g1=C}0SFN=x4fgj}K#L%_6eUbvTCdOJItB_b z_=33H#&EBRo)3_zZlOGL#;`J@#r}Y|0;uNZ=}9gRfH%MEn9F`VDH1=yg3wj`o0;jD zd|G%RsWPrN%a(B~VuQU@ymBr)a;tkH>TD0C+ws0~%i!XY#8oXv^q98{Q zM|oks|6bK~!%TgW0lzs@7T-HEvXArB?yz4++2-5b6QGMix=$(=!WAX3DoJn?(HY1| zANCm#kxRtb9H1Z96fi}rRe|@+Bj6}-;J{@l&^A9_-Go;D3a&Tg3&f;|nk97yBoMU$ z(@q6Dc%6!Ne(jb&rLv+Bro1;O9IuQi<=}!c%*Y`KhbchX7g}2b{EmD6r2q(tPv5>}#3@uf1d9=f zgvg`X0wgtLk#ph9z;Ys6-LP{r!qwW^+9Fxe1NoEIbtU&XR4h%e%B#QPOHUWP5H<5< z%v`5!)CGWBF?A@9=_`jAcDlcF?hM<$Xf>EiipIuW*R0Q~Y_BH*y>>y=(t}!ad1P*l zVYc%kHbi7U4EQL_yI=e9YMq^(9l|XqUc$LEeSJG_NM#3;# zy2VCfx?ZHrh~L^ZXA=^=8;d$%8Z$C}-KSC9))!f8jxYi?AM6-6x%xpzj4$n{%%GPP zIevWQMXv!-lWlD=FtD43hNhRT&|}sL<>bJfs;u0*1)cHVhn?SGMBliW?J6CKoq(Wk zeft403kAl`KN7;r5zME({c)W)vJ)R-f7URW6#~36`|~xuT-y|@i?q4Mj2K4O56eve zp8uCF!R#VQw_sOdO9iVP^MvF&3`7Z&Qn^03`m8QofoDn_ zQt0HE=n!?AFa^*@u;|L{pKo~K5VfZ~mpYr8J^`mC7uaUKH>1~5;dg&@XY&tYGG*! z#@B5l#Bp)E3e0MlR>>GN<+Ir$ENV42E5M%LAZx zsY~0a2K@rUn< ze)q_qKa`lZKtTQ(zABk&#Kyohe3Ml!8K<&olUG*W47(599}~&vi``!TKBgKrgd90; zUitm|_j^-O;+=T~`%=q5{%ypTLud}}{)Wox>aAisRYlfXuZGUppr>Lu5&;g9c0y(i zw_PY;NIRzuTI6z#@A4MdU5EmQz*#oh&YY^P+P9DGs52#uF7PQbJ&c(G8Sh2=zDg=C zw>8<_pYzzb;V~dmX)CoWHU6ZUBRI2XbYgbHH^?32q8NyM1G%ln8?xyCvhE1{qKwHb za&#ek^sYLL2KVDi0>=i#JtwB7=%2OYa22nuE|K(E$=7SX)`2q6Igwqyh(HD8A?zIP zLkzb1bjAOA1sOxy6DpmCJ`dulG5Hq3?T5rqlzt$5q0)Y0TOw-ZGv6B+m*D5UIKw3& zp?^pZpD+Ezi>IJvc_r^tl?K7W&~4$_FnahS3g)Lz(v^>oIH8T+4j+3UY9DDnjZwCJ z5@QJo?7(=xTeCR;rJhQQ44(#)WiRR!cJ8$M=am&b>T)!mco+a_*!KZZpBjGIgKWV? zO+z9avp$r}^8kfpVhh)`Kw-iFKgQ8j@b+0p52N`zD?ufIa^n|yEvL=jAvb0FaU@u9 z@5ElIWo)eS+qyp+?B3;ri!5MfSPtFumBW764iGhapzq52{e?f?gZON*0^AGLq zai9&5MhT}!5g-xZLyFyy55dzAvHNm>Kl(mvUS8g51A{uO0QNDS^aJo6a5CHZ1o(g? zFc`AsJnlzvart*($&(PpZl9&h`MZXOhQw>Z1Vl0vX7Cjt`>No%FA6lTG0=IlaBUWZ z!W47qDZN$Lm)qmU7~K zQ5}?Lgret-h6l*ja{rdO{4^_Un=PZek>Q=l7olx!ZIF(L2MCY661y7)PI7v>>cA&m z8l68>ySHsN7b%|b8^J9$oT8$DN|*T zEqsgb`#$zoZQgKAIN*q6`>b7FpVKkFz5lzTPXwVI5JY0)MLMO;!P4NKX0(ASAx=!p%%p(!;Tdi?8y$k2mVaE_9^AkK$EzzTGcydv z{0)NS5r%?Zg75LCss`~I(xkVsh~7Z5g^U418-XG6@%jI6e~o*imJ^UB#pX9Olj zTDw#?oO?5hOx6It>@&=$K#6GS>^ub^jVY@v;GDL#iEyJEFA-Eg7a+HOyuJ~w#tS7u za(NFpE-nlR1msC>9XB*E@OK-`?FWviG#7_%{nh%Gil(MA#uH@>vyi+-12d0|IfD{} zhlWZB>ke3Z^m_SP*YgUC9ID2bdsM4BUy7W=&>DmQ+|HNW6l5e^cFErzp(}g?be_+N zvLZjFH*DVad*^2yagtF$LEQph?tG!MAR4hL6|aInRs=J10#h$=$H|wUKSN;3qP#tO z_AH|}<15?P-@oRVg~22TYk|>cWb^zdf@iis&JDmWA{jx1fyt~IVu_RiNr>qn$J(U+ zk}XS3Lj9c($wC+#86fI)`a?O~4g5eUc+Y z48bq$I@lMPafh%@6moLK1|IU|k?)yEO)CVgbbQW<$eJTl@*lQv@F4sEsTsa?4boQF zkLxLW5W^~R6@ig5h)dJRd_87bkfwkB;spZS$n|^1QXoqanO(XVf{H^DmSpGN>;X$Z zyP%DNK@JVlb0l(vqgNl!r2sMP2zCW_APHXq&|!k<3Mx0!J3Y{#9v!wO_l`k)B9^q9 zyE_DlvXOJo=nq}N$0qI<)Eu&YaxC?Ab>I*8aguPS9dW|Cy1IZO&|L-g@8=N_xreSU z=00WK8_9XZ*%vZ$F=QTiEB5doHq)?cz~X^cNpHFJ)`#~fhLkik{7|A&b!&;!j1c6; zO}+XwFL6>}8-Noj?SsSsrIDn_upof6_P8se6}Joa{_9>_>4s)skfJo}yQ>#bfj9VW zZQ!d4aI2Ayp(`~8)y0`oQ3;y(6)p4<2!+V5P=v8fWQS3ac#AU z)PUc=epQ3EJ;(JymQDfkawJE%1f-o~dix%pJ0y;S0Ka6yLq!Fl7^*}uq#Z6_=EY_s zqgdyDsI>OjOObIFXpV%AW3uDo1pmbe>_{nGONHbn1&X67S~eL6fc&<)(!CasW=oQq zxH3ZyHX*7xjuW|gCI>`?YgqfbF&`| zK=5J&WN>{Q87t_~*vZHkjvKieERqWgcbk})czJtoT5JQ?!Ce_3zcBSlkg^zeC31fP zHA_X742|s-b~c13fM9}7mXXaENL*Xy2Z}}C!Cg`}jI+srF1fA->rHj04cmflyc=b zT$Ql}q|xNk_398_-X(5M3DG?2LVMs+84FB#qH|_JT0V~?7B2QcTpnKr_zM6I<7E&= z;TGwbnB42MWq!pqyhH?GLBU{rN^odP8=C%S$NY3n-Hc`wme0RcSKtw`JjRKh>6$YqD^$$G2SS?s9FRe z6T_{I-`VU!q=5F1R6e!$3Co}tm-_Xhg@SGw4JxRPZ3oCDj&uIu;?>0w*rb$H{OJ)w2k2Erj$r@|;Tv+@ zAVNYiF*>$?wFS{FnAR1 z^rp>5KC;b5V(w3&`m1fK2Vu?LhBO4aXps4i`J*muFcv+vt-jvt-Q3(Loie&ZqV2x# zT+6Kf9VTiR85N|KS}1H+*wmfdK8is<%8(@-8zlM2eOGI$6PU^P??RZzN1}?xOZVW~ zH{|`RNE!zh2a&N5+yt~zB30H-waadPH-MXr3_9wX{ z>-IPdCvw#%67~8SyC7XbGDLR99`{lpA6}0IajZDq(Q8lnRSEJg`3iTZeun+E*pwW% zF5CBlbfFGc?V#f%k?Iq9PrtK{E5=kk4g&VR44z5btBbenTkM^j7y`J5Cm>0NJg>%$ zGC1DY1kvZj)NL!e9YNJ+6^1o2|X_dGk3ix%FQL4n__cHSM-<;A7I z$c|vky7Dw#&$&IpaczdTBo8+oV7-`5nwj+-$Uf`W3U>^pPMB#8sxX9(4S+ke-oZG> zxc5*K(F784L!`&=#vG;%s1>X14s6uY(gJ%92rsQ4j6}2~t)kZ+N|q;_^0+E9hnzN> z3qWj+CuTDm?bnIpvysN!i95TX>oa=4fX4tpbgRwAqUZfhq$J4gsSORO2*m?ILgK;x z?tp}XZuIX(wS~EPP}R&x0B2KcQBe^n0S%tG-zNKHwZEg{w6^btJ2g+wDJK^dVR03) zS^&JntbybJ>dX@;4+xGX z{l>*YLB=M}A;up)`iPWf!zJR|`uPdq2Asme#k>Enq%)7pDc|FGqDYps8QIz%B}GGb zUUcOum7Wahk)j%r8j+=l$TFf(mLl67#XKn~d!!OCl^S^^OJ#6PSDP#;YhxR)?)&Th zJu^LL&N;vD^4U(zkE)=j95uA0WGJqi zaSoN4e|Y!KK=%c6o>9XR+!G#`6}f2~o?$7l73Ah!MKHnoxOQSz44go@*{0%@1cPB?suLxV~gFa#t%yM-z6eX-6hZ1vpw> zI4IA*E$7Uc=$da{?@K3qY_xlQHxa#V(xF2E)2B?CGC4Ff^Cj5tE%>cv`~=8N3=h@` zF-&U=+QCrlapFudH(@m}JUv){*fN;xkDopzY*~+OihP0KYATOpSS(rMcFGrxX#CTY zhKH3dBLIZ#!B`o@>vJqOg5}%yfgJ{Jwm483Z#R{(96|@me+=*%j3OFSigA5w>)N{1 zwy3oOd5r+6Neg=rAx>W;ZwW))HA$=I>*PTUq%}<{aW@`DvFd)fh z9<%tGadtKAn@?znaa_!A78qs`fVJkV%ir$l zm+gax3wxm_2?%qY!DbVcuUcBRpj>MS*i*Mnl?}t??bAsT1XmoK-;+d`OqCoIBwqY@ z;H9Vp;3eJ3@A0G{1$mH}VP8YoOwPx=taBH}DC>hbE*JiLrfwzKlXrd+o*PP#nX;15 z3Kv(`I20>41T#m~J`QIp$B5zpk6|^_ICNUpjBTj}g@tb@T6b$|nmngZ{}2%!{XuZL zH3*IXcF2MH`k|fqWeCLj>8qVzU*)n#5g6wTNV@TrM}+Bflg#k_r3;GccCp*BS(J8j zF7+p6QP+BRt(D5!5X-$_^>0%dshx-W+3eFi_9S8~f^&k<&EoKJScHw!e`iY8MCuR` z#NX#OV*~7E;_&R^?vAT-D9C%*H0C)TAoPsAgnV_TmeC+N{nDUoM~77Cv5CET{aWu- z*M+gOZH*~n_y$}?p7U>QZ3SS-0?C3PhPspdQT}tRhtf#iln>~o&Du$Iz~(2(C2$>t ztDk=e1$Nb|%bwyBXbPy2iSaEwG54cn2^z6G-nqu4+8FC;>iN83N+&eUWFBpgE90G< zo?~9PVhPD|P|a**{uJ5!(L#o)c8?3X32H#BsZ6ARmgfC$Qt_AOOP(=*R;_ma8`yah zbRUhkG<$mKN9CFfgnkodQJQ3ihUtR$msBBMl3ai@_!i=^%WG;2 zdVDf7Q)_dH>6k-RqFNyFhjfk;NOszrnkJ#OYNZ_|D=aOO8EA-@XF$-jx{rp7r&*t< zoH(B*OTH2*p6~Z(=skS&XdnXxH#FK83Bj(e#%@^jg=@V zDM_Q$bD%n7!pVD!w5&f?X7SFsuU=hnXJ18SCGnna2crnp;eUi zM}_+G*UhS4;RI#v+GT8&%6`mq_sN7R15_(5571mhw58~M)w93F1Tg_oEqWBArup>j zXwqt&LuKLQi-^7o6a#==QtrX&ETV1#Oh_st(iH>kRrF3WxKfAN_jP4kW2yeQX$%XNDAzbd{G^F`7z3VM)xbuC29n zsRhIpRQTDmiA+bm?~*VBi^&v$Q^RGH`8<3?c>A!?OgjF=om}Lp&2%dI=3ACByaHvv zXZxN&0R!oTrVsW}RJSbT4H})y8gj-LEqXEY^A@y%Ecxg-%`TA)Ne9!BY)8&@aF(yN zp;#SQtdY@6#o%=S4m=;(wdUIs z%-;P>19c+JWMDexhk2;jEVPVIA^Y^Iu3t)r2{{iv>loAC61#=Ew z3K|n+psx?A{{;1WFit$pH|LP_Dlc_*?EB!K8^V-l{ii%Ii%I76i(=Dv~hC93Pjk~4^UsEve9gH&amJ?mwA zoVNt@Wn@``1gXt^O(HTZ=AXt1~61k+CDCS zs_nRyFAP!b7B9^|4^hj!6&JQcXs{?p@LG|?&%$q#Xet!a>Ve(dn`9^ z?K3!$h@{|idKgq7K)}Q21KjXuL|HP=@g+O~z$ljz3X%S@uE@_}z2dIhjUX^3&*VQW zZO}HgWey6#-OD1*j@lREu8H+qyb|!k2IT!RoM=HvGFa+F-h?k#12(d{QM9menA%annOcF ztY@Z3;J}V|VTllWu&TPR$)ls*rkC~8* z&W9f`sL0@qdh7d$`iTf$AnPrOXk$Ff&CNxdF-)P*VoJqGCONEC;D(ZvDk&^*yLeqh zEG(gY1dIqjORgU6NeuFQ&_MK#q=1pDZWe$zE&S`}4saaF9YeZ9`{zbWCc1WS6NxKD z-67sO0~_F2dIEm2Yw$mDkHh(wnO(&<;$a3Amd1TL%tlRPkdKK_Ls<}Lqc?8eB;z9z zFcL}}krfteQF@_CSjA%kmKE-nk|iGs z;pbo<)If;5)FiKvXjJK{>~4F}BzTjxCUBCCO(WeWkiaq~ zWC^x7GGRU3Um4M=z9*2BNp2^|S4wKCZOCQJo^IC75o5VTar>QrX#0678hC+NIDG0% z$%JKqm>W99Y!xpNgHn1vqn-?XERRMu;a`_LRdzG8 z3{bPsZ@7S1UKY?XMd0)D&q4|KC!gurix>JI`VSd$iz-Uqjl`FsS{DSA-2>baY=VVD z@)|W>0`VRo;H^jXT$nxn84FcIQyo zx-2AHlpRu0KhE^q&0oCVfx(4g+H8-vj@zl4=iMCKMpvSd;JTNC#d^mgH$em#xY1i- zrFmn`Y1$b22Vo^xgYwS53|2X-YOz@E4Fjid1CpJ)OzK3>Fp+U|FPNGa^za zF^0#xWFvda_QAq$?fHo}Y>;D=hpiq*g*Ql2^T?gSmGQm~Alo&!y{*lzaTQA2kdO@P z+fz~ka>n!GB#d5*@UqX=Nrpy3!uCudH<#PS7$*09)(#)VUe9YJt-eoZwUJNsn4OC| zpHgN%(8MI}=dG4GqtcRD8<{G}i?Ls~-zG*C=~jA0sl5FDJkHQIUFGs09Z%UA>tYVR z&<|5r#Syl%g<)axBS49qb~b5KK4d|Q1EGZ8z{a(I!`II`Q@4maq^8_&h7xYv*v z2n{(U0P;N_AE&MKoHum1B02dvH=N@q$l&F2I8=Is!pds$_}l#b|7TEx5oaW1XYai?Wn`1A${yK!lfAMDNq+WTA=y!~LlQz(^ndRE z>Zp$U-uFJA=XtN^6RD}LKukbQfIuLKl@w*Q;qNKdI5#+bG%Xh@#saqa$h8{9cpFFX4 z_CUzESzCBmTQR(__poD7P*T%02qL+OKrkSbWTkXH=XW03$C#{7`?s3LA3qVz?W?z8 zNq!b+l_behTJ8-z&=sb;!S?=!gukwYRv1S&$DTV zhN$MLVlD&O!=pQ8Di43)>ZLdT9ndb0+)t{g+(~@(KzClUqv%r=LE5#!nv(brOhP9f*JI=JuAZ;D>g) z2Gg<&Rk<#Kc;0pSBC=3vtR&_xE8Z^4I>{vFkRFS{w=qFMSX8m;w$w-Xdg=GtdRJYo zcyIk@%JoW>W%G!>!mq(NRJ}A99-}tF!|N|ADyXQbyVqYXJ`1iGPB)I~Ls=Pxjco+a zIfcRRbeRVZSxF0Ig+8iLXfnk`7;;knx8S^aa;3_5M+f(c6!Ry1Bm1>Qv6RdBss%LkG5#Rp*0->W`dWy#V zJI(tSH0=;tQGrfX)(B7XAZ2?CL$j)&l;BKoxDQESMFri>n3cf$|wv9q@? zFZF$P`Xj2MLdfroPeeq-yusMf;f_+0X0<+#m{@FIpIpkY^`?i&o9c>b_Cs$m8WKDw zf!naS+x)r@+vnX5H?`h1HufyLblUN~O{5~iMFcV{33=`@z!vE0t#9g9>kHqh(y!#s z8g&uL$r~!e-0!_q_}oMb3k!Sa7w}=Ysbig(dt)N{EU9Q|{%voM z`@=f#h|T@dP^*x2w_8vV=G+W9>h5>-1y7>@7)^RYW;7 z5U5Qed=(`!b92KgD#~=(6-y_DT$T{N;`Gc)(lRnv0#R-3-+bzPj-3zx{6QruGUScP zO!5hcR3swhq`1;$(8z9BSlB@4rgchAvvwNqw%lDuZmPX5JbGV$vI;{^w}`6Y)YKw{ zcocQ4rH4m~4>P=zP5o(4?D>mjP9<^=5!x7eCQeF1c!<(nheG)I{6UpIhbh;rb+TBE zjj;Q7BDg+wP^Vl!j_>E%g<6X%%u3z#|4tNQVq^E8;YfcHnaKR+J|_0L-S0u`qkDX6 zGUd9K%}L{SvYeDM0RjI~1<_~L&w`uZ^78S8+_(Lh-`JS`;Qa30yRWjdLuR+H?lEqR zI5*ZalKGXGa>=Aw%c97T1XrOm*ABe0B?9Q;B`$^H=)?%3`(A$kZgY5e*tvUrAl6~$ z_Uo%Kbnd%`hKFmM_|rx6eS z(pgy{r{N|AvgEj_WEn{Rdy9J`egJUAA*!?aukG)Z=zHDEE=##Szk;CZT~~0rm${pp zoA+{deep6&7?X!wI$j%c7MgM~r4KXajTLF4^G&&mV7ZX18lw9+>UrYCdV0|7%ln=# zE4|mO>W$XigiBUQx97Ky3Y(g4J$(4k?&;I;X@|BSq-~aU5$nV0W)lTEeD_k7ow&Ku zqw(;|H`Y8v3hb$&*38W4-#g8{H02tQXQs|BM7RFRie|8&?2fkbIW_)&Z%nXB#F!%JN zy12MF`SqeB+K%sova}We2`X=_K5<;v5h|-fud>$v!aFR1Fcf=Yi%;OmyvLC4_CZQ$ z=+)Pg_En}$zaQra-@>jQI6c_lk&w7vG(H$}t#mTdiuc-5kIim(H}+R&L8d_D(Y5_( z`Jz{Oc?!(rT~RkUmfV`HG7aHbCrZX6io;8EPvleO>NHM`5-_xG>ppPet^#J2@H zcb*sNvRgPilhoJOzk2mbl9RIM=TA->8yl+B!fdl7=2xROHd;Cab`8c&zX))H;okR7 zec_?VOm1gq7dUPgGO!w?Ub=b-NC=Qqre6sN86jV^=iO%5?kfzSkTk>$fHdbMZ(wi} z*rxzZz>&?YBx-QzwF$M`vt82>*WNA;rNl$=^27^=CSp94Xl1Hg=M~^WpCtyC7n}z+ zH_=cY`4#N2L~s$;i=$a4=+e?j*Led@O4!D4UK_Muy*6?bS&~J~p2-ohCo1M^q9scw z3v}82zV{8UyVcG)(ff=7R*}$)6SXXSEHKua&g{>EdzXF~qB7*8!=rSyLNShyibxY# zT(T=UDjM9?d0VSmUki-{1g&$JW*4G~qn-+nT2;#uU`!w0UvbRrKQ5Z8EGWPNcml`) zoP)wsEY>!B?{o`r9LNkhzoevuVVKvgi6;I=!pj7$aiZ&Nq)*Gn2gj9@n4t%=MV=9G zr4z=+#!}JKZz$akY|LHw*$ehm3{bUS9@X^hJP)X%sMcj~l?Rm9(b2&Vm4+>;{j&49 z$(>ZD^Q%qG3ope-6N>F8~tE~-;i;LrUtXWYZ zJ;?`mWRxcH2TSf+c+V$3;$@dt55{(OcAU5~RB@xDqdhlrUT}l72&ePL_w)1PmqR_F zt_$h2p}7?cEZ$|ll$XdHnHnSAUSj_$BcluIK4EzMWJ68{!(ya@3mz0tQw9mIAR50A z#}D+3_u27DYayYth=_*^8QJ1pC#rJz_y8s%%qXB3ChKo zH&-rxDan8U)#4%)^YNp4m2pEwiBO4HKA*I5mCC06*%pz{Z(bSv=z6agq#y%gYv@cb>y*J=-4f@$tDlp0ML9H011d5;)jp{Xirp zF?vWuOl;xgL?k9AMny#x2-r|jkzk!c8#KGUj(*BVz3d`%BA%fdR`jD7EoeKI+Xs#P z{rh(Zk3dfkm4A1seam&Fc{5~-wU^IAm;BCdozYC$p1rP;Zw;t3#5~(n=J=)w_qxPi zZn&`rR4aeP&NhoMOA2-WePhEhH}sE@hpE*&gOPk7TQ1)bj_ z1uE<6K#iEYxsg{?thAs1YI%)Cu6?An^?GoOoGE=%Nh0#a9cR*q8d*wXZsm*h?RI==HJL&q0n}~o?1YZm^eingAUc5rE98#nfwe)2C>N6#m4Rx3%YUwW zTxA|A9h9n_^g44)F|S1v-Ray|1O#<(Z~(9ja0wT)17Bgyn>G4VlTU4ROr50Hiq{pF z;ZG}wsz*LM{2-Q=mzOm>;BJ+YaH9LL!+W}{G5UC5)x!3Uh)l)x8*!LyBb-it{;5wSi$N!&c3nMkPUO< z&Cp~|{me1Gh*K9ur(84p7|6tNrV2=*=dJay=jzs{>uQtS+}wfCn!WARl#!KCC8R@pvF`rW|#q zRAmcj{??MUCbn*!9L0WgNr-N?4y_cMJFwoTPo%KvaHa4EyRFIF^BQheDzxUHBwY>PK1EY<{ZayHIW6Q zOx7bd_3&GG*XgQ+nL}Cw%5}Ses}be{akO7E^S8^y^CM*Y1lg2}wS%Da_E!g%kI!8f zp3N@rE%$&+8DY;KQ%q(di?zSD* zI?i%=Jb&K3d;HkS3J0(s(|K!a%(t~g=?1!j@mx>#EM$wcKvFs@PK06H22>qCy(#A( zfJYx|*E%pZ83D#4cUSyYfCh7!_P|?a6D!P%XF}(9y9qhMCYjB;>ckt zNC1nux7M)e00k#UH36|18Mn|;-HAaqYM}5-G3IJa^nhq%_bn$ADLzA@qPf369ZC3= zX@?u?r4+DsXe5EDO5dt0sPEjNgp@~=1XoK^NPntdZTzxhQ}#-2;(s5Aap zZQgz`_?C5pgvz-ON0ycLiEys~99feWI49nhHx>P{Jf43Wi&WxtNTb&4zy=tNS5!?| znGL@n&2kF06sSFzm`LXI<$dg=fg7qYy(C~Vb6izZB&UC5L{-hBaHG+X69kt$C*>;g zE;O09H+7c46KV0h@X0MJT81gkys;j0Zcx3`vNFb#!FbnK{(O0=P@uWgMw)1lxD1|A zl|_emLV1q-mKXHRVO(~)dZ~26jNEhSNm7rymWji#In2AV8W{~L~v`>CdybBeO{~20dK>%`Z zFoWt=UoNHGy?MJjZs#XY`ZNO0bZ|L=A3*GafB@&~GRi-T5ySw};9o)D?XrewI1y%x z`A`C%nQ{o{sQ-DNuDrN)P*(9_{AbffZcn*RskuOwzEV6?uF!HK7$l+HOU%B&D;tIe#{BzMINz;r)c;xAS>3GK=vYl-%|o4Nyu^{>y# z*k1s~uIvxchmURazz6*I2-H(p81Bf(h&j*!h&iDbzi70}k>E8R2sYmoCeilf$)Pxo zenpoukyx)(tc@XXM@Np2*}}oUemUDHU~EmACeFylK~=b}F{$?a!a^*t2*`BZ=37}U2>b`pf`Ll^t!KOMmbRT#8^AkP%B;&bV-MDwQUBg5} z(z9{En5vA))p~wRSKj+jca4oa2=cSxa@0k^phCc=@sDSTFW_=CcdyMA{x!5Riip)R z7K-Au6q9WT863=K;lK4Jf^_^KLZX9jhnG4Q691 zmu#e4-vU(|Rk&1~{^;eG9eG&L%*@RHgf-43Nusl>@W~SgrfV8-gZFv#<%mI&)@? zJAdTuaDoV&$(nC$)4CyuiHV(rpw_mjR%*4>6mb=`?&po&cTye+c58~cE`EX#$cl|M z(L(;od`Gs1vw1&4OaHL*-`@?1ec02-phmI;pY}ID+x|2^|A9n0Kdj5|+PP8UfPWR8?5UgIHQq1reVnCSJ1UdSd%`lQ7~_(h2e&RIX++A9l_$Nf9waRxUFPO~N9PxNo}w7}4e{!N zb2!L>4KU^4J>dJ#n8__Zkp~a<8*2P^ihSN3#)BacJzY!oTn@d-EhuOZ+!`4>28vJ? z)kUb{E_jp6G!XnZ5b;d4$pC>iCuI{yt}4qo+~(z_KQ#5q#qnZIkVN0h+?3Q9sjsAG zsz_RNTiu*fc5b9xBgD24-Yz(AAmiK|c;&S{D)IGvblb9`heQ7uh-azKnH!?y*NlE!>adE6w0$UZ#I4&;kUJv~xsfO4Q zlAc8AV~|JirQgA*;3@=pA;4E$>6MY6)>8V;K%K^Jyw6r=b^dP|H|~S(Q*A$GCZtME zqR@5X!&-Gny&-%Oq9OS>0#WbEzL1sCcYhAV;qmcmK{(x+=S1*H zA7;0=-?Wh2Yu&?+qkRz8*VmVMNy3J@P>WK?njIexBD~3!-_nxha~A-1-;)N9gr>9O z^5|ZOG~?gPxz>8>UX|qiz z*85;VpobPP_PxJf9#X22j~{3L#wZe%ST61!gNAk$;VgNMau3m_w0s~aD0qL{q}BiV zb4pk?E16NK5r*F8&=~NcIKfg>vGQL%S7Tj-Xu#%!WBL5nnh+C~?eDv`LTI}A7;gDUUe)hE2|Dj@cBEW zSGtWbYEvdLTwJj2uakuZR)HpdRN)@IG_Ra&YQLr|DzNOqYr>GKDa&oe-`BIbnh6`M!et>LDnj-ocnSQYxDqdk$M<%UZfk2W7 zTifloQ!jqLE{KAq?odKl2k5O%2+J`{4$*S!?++X&UDy3Pl^;BKU^2;8qswmC;V)Ky zXV3*QK?m{ses|f^sjPebb z@{5bFUKcwg4Q5X9E2|)YC}dlWpQ%{2(48Q>hl-BwjcYCPj@?4hI2r;b`qc&xk-*%H zKXJSXz%%mF>OIbl?rmyQXld2QbyNzD)HjVj*uQQljtMtLrFiS?$OopE*hBMxr&G|- zxQ^M$8yxzWXdZ&Ayxg>7t$*W-i}BFfUtI@iJ&zY&xGr^KaY7bqSvNHjq}litIJ~Wm z7Sci@lRU_c!>`l#7s!OaN_3f26STmf8>mPyP16q6DXLEGQFJ!t8)Smbn&_$gz$sgD z;snv6S7Vc5>`^bB1WfLu08cPw`fPh{We$CEx(uH16hX1<#~JhBJ*AwCZF=jLY|-rnAx+NWiM2 zx;B)Ij~i@gYHC%MNNJ{pY(4#+CFJvm6LcF{q%0{xD1=q6U!F7;z-qU(wZRDI>j@Jg z7)9iT{4g%pgG!LCdRCT3ro+L5t?5xzf3Mfug>6aFS4K|jbKusyY_RCQ;$vP-3(mH? zilO(5kyA!D-F;ssvrTBaa+U-iI>B&7OOJ;jLRryLAd8F$7qW37-m%fqedEkg8=$CZ z*(*`fmLbe?B@x=}sVD9e)Oq55ncI?}rK(LDSHf;PLx*zy*gG=1u}KQ*0MPiPPY{#R>-y&$;>ikjn6uiWWqlT=KCMjJt6R11a^kfQ1pQ5^61KdM^)|Dn*5Qs&t(Ya`dATJz7M-j0I$hMal%;8c^7k}SFpBow`cTpL>Zt#)}Y z8%3z6Yml7eOG=%eVi75%yqsC1VVdZW)6>(;OWe?N5Ez>1ULpj<#Njpv8)(v|<n0}A026kJ^nr|$iSaEvRR2FD7*H=bPdOz zUXFw{Nc>Rj18;9)9Fsy^erYKlc<7#J0Ssu zfF0}Enk-EmUWa)Hj3%2{8$5z!)2?{kX^!8tmW_X((#A0HB7$CC%N__0Vsq(43nnl}vf7m6&+rkuySsy)05Fq>m`}gv5iv|yz$rNi5Q4&kqh?O(AATZm z8xnmk)Bgf7Gx6hJ3$UpCiD_q?5Xo+NP_Mgv?Q5AqAPD|{7U0&L(|emgL(Yw6vbg%l ztB?Z+<)+ z710U8aI_3bMGmY=@lne`1Pcsy^@9~JW?sOt1$mn)3k7sCOrQV+ z6Vyw+BsIVKl39DSEMRc*K~yrU2By-#Qn4yXjY&12*pPA~k_;|n4+3XoWG8zKOpP`!@Qg-vik!1?X?>-d~ zlrfBM4V&EVUH z6g~SkHwP1pu4ni+4pt09201AmNzNp+C8-%%nPU1ZA<@CGx7oe71J?o#+r0TviTJ>@ zFu@NC4|n~&rUbEgob%}Ds8g90DId2G4-b}6n%7Fo(kUo>n46k|panjM(UnC4q92>iwtIRzQn>+%iTbN(y9Ix2FuR zOT$P*h~|xOK}1Z*kLyv=D8{4-I_isj<7FMM>QLRiDMhE2IHSU4{jyn^F*s#v+1ee(Dz;@ z+krq&E@DvAYiwxf+Blf5y^W4ax}vF^L2rPX9eRGQvO^jR~B=<49^~j0GGrLM=-dkY2%F z84_O^l3yV+Vo8o9j!Ll_%M}v>EdlWYiRI7-rn`maA^d6&J!q5^qIXQ+c&+l^R!yeQb_JU1; zGA>m>7MF36mh;Q17(>-vf3DrkI-^=RVfMq9glB?cC(7I9E$0DN`r+H}z(_dQSa4Rs zttfZG`Yem+zk-4wT9V=o7;M{q1k?TM!SSLNxxrJf@aYVgSGD#TbA?`&*h zQo|JtV>77D>}goD~a3hG#STpZc&ytMrMqM|V{Ab{Me z>R}5dWpwC3ch5364DA(U*#Cl02iN0s^8USmKB=76(($=PogtNpWrZykd|ve$xT+S+x-GJ-D}D7bH0I)E*>x7 z@*r<~axxe^N==xSo8D_*6|D@8%YsYdz6m?Ay8oj4P^DD5ObzefOY7-j4nTC7|Gy64 zG?a7m77HBQ0TEiz(LoPy2D(%!9%h23qbOt zI4f?r31iM;xHV-Om_@PDjn~5`frAAY{R9?40aPaJ*7A|}J(0;}hcq#tKTC-UbX^=Z zt=)@0Yl#Zt29KM6;y;7L4PL})@}3A1AUOMxXM#?*ZYueRn!kSIKb*(5ytjaP^;y&= zA)W)-jW9}Ec5Bi^BR@fg;rb=mdYc{v%MhiFIL*Z25Ml4uB_HJ>0`p(@@kl{~ zXw7yB7(BwK-3!_WU+mo2@;zVW_XIL%a1Y#`P~rG7MqA_KI57A}*{ytjAMqwqQ&^4= zzqX7qnGYE6nz5zS=(ea9CS zxn;sfZ7tA_kBH0;%d>d{Q3wbb#}N6A+ojlg_v*%dCPf`Zc^meUArmz$<048I(}t~KAPnBZ0$Bd2?F2=g zGU(4T^WtG3I0{QUJA82d{2R|Fv*`K`ZrBmaosr4Wx+-dl`fB-pQGmDrvNSC`@^((L zsPDFK=QuT#{im&W<{N~b|1=zx`dd+fg3~{#$~nC?ws`9^Y0?Uk=}>H7ypgP#adccOtO{hS01@z zss8wVl^ZQ0Au0N#f$JZuY}B3dS$;FxrYZwZiY%CY(pg|mPr7B`%7x=hWOzO+S9y4O zCAiS&m9O}}#N8qI?+@G~won%3`Z-Q|3pivswa!aSaI$xo2n>qGwQBe|_TPKa6)%LT U(^pL4@F+q_PF?nmwE4^b0nM_ag#Z8m literal 209 zcmeAS@N?(olHy`uVBq!ia0vp^SAf`o14uBqJF!g!Qk(@Ik;M!Q+`=Ht$S`Y;1W=H@ z#M9T6{T`D94;$Owbqp3jA<+`oh!W@g+}zZ>5{8h(qQtz+Vg=9K#Pn2YAJaCV0)I~z z$B>MBZ_hLGGB9v3FUbCXZhLz(o6qO-ZeFAVE%r(G8SAxEHyZ+tX7F_Nb6Mw<&;$V7 C>o;ov diff --git a/companion/src/images/library/00011.png b/companion/src/images/library/00011.png index 802e9885a8d41bc2573134d0c875e5e07a120834..da65dbcb3ab97eec151df264f96c0d136470d28e 100644 GIT binary patch literal 7407 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 OL;=e|WGkdi0{#cTkElcd literal 209 zcmeAS@N?(olHy`uVBq!ia0vp^SAf`o14uBqJF!g!Qk(@Ik;M!Q+`=Ht$S`Y;1W=H@ z#M9T6{T`D94;$Owbqp3jA<+`oh!W@g+}zZ>5{8h(qQtz+Vg=9K#Pn2YAJaCV0)I~z z$B>MBZ_hLGGB9v3FUbCXZhLz(o6qO-ZeFAVE%r(G8SAxEHyZ+tX7F_Nb6Mw<&;$V7 C>o;ov diff --git a/companion/src/images/library/00012.png b/companion/src/images/library/00012.png index 802e9885a8d41bc2573134d0c875e5e07a120834..6d1c00fe3c569acf3dce938adc8ca3f407e3509b 100644 GIT binary patch literal 12578 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 literal 209 zcmeAS@N?(olHy`uVBq!ia0vp^SAf`o14uBqJF!g!Qk(@Ik;M!Q+`=Ht$S`Y;1W=H@ z#M9T6{T`D94;$Owbqp3jA<+`oh!W@g+}zZ>5{8h(qQtz+Vg=9K#Pn2YAJaCV0)I~z z$B>MBZ_hLGGB9v3FUbCXZhLz(o6qO-ZeFAVE%r(G8SAxEHyZ+tX7F_Nb6Mw<&;$V7 C>o;ov From 961fbf291bd93ea98079851a9d09703e981b2352 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Thu, 27 Feb 2014 17:07:23 +0100 Subject: [PATCH 87/89] Problem when changing v1 value in Timer Logical Switches --- radio/src/gui/menu_model.cpp | 33 ++++++++++++++++++--------------- 1 file changed, 18 insertions(+), 15 deletions(-) diff --git a/radio/src/gui/menu_model.cpp b/radio/src/gui/menu_model.cpp index f5128f20e..93e9a8f52 100644 --- a/radio/src/gui/menu_model.cpp +++ b/radio/src/gui/menu_model.cpp @@ -4559,11 +4559,11 @@ void menuModelLogicalSwitches(uint8_t event) // CSW params uint8_t cstate = cswFamily(cs->func); #if defined(CPUARM) - int16_t v1_unsigned=(uint8_t)cs->v1, v1_min=0, v1_max=MIXSRC_LAST_TELEM, v2_min=0, v2_max=MIXSRC_LAST_TELEM; + int16_t v1_val=cs->v1, v1_min=0, v1_max=MIXSRC_LAST_TELEM, v2_min=0, v2_max=MIXSRC_LAST_TELEM; int16_t v3_min=0, v3_max=100; #else int8_t v1_min=0, v1_max=MIXSRC_LAST_TELEM, v2_min=0, v2_max=MIXSRC_LAST_TELEM; - uint8_t v1_unsigned = cs->v1; + #define v1_val cs->v1 #endif if (cstate == LS_FAMILY_BOOL || cstate == LS_FAMILY_STICKY) { @@ -4599,7 +4599,7 @@ void menuModelLogicalSwitches(uint8_t event) } #endif else if (cstate == LS_FAMILY_COMP) { - putsMixerSource(CSW_2ND_COLUMN, y, v1_unsigned, attr1); + putsMixerSource(CSW_2ND_COLUMN, y, v1_val, attr1); putsMixerSource(CSW_3RD_COLUMN, y, cs->v2, attr2); INCDEC_SET_FLAG(INCDEC_SOURCE); INCDEC_ENABLE_CHECK(isSourceAvailable); @@ -4613,7 +4613,10 @@ void menuModelLogicalSwitches(uint8_t event) INCDEC_ENABLE_CHECK(NULL); } else { - putsMixerSource(CSW_2ND_COLUMN, y, v1_unsigned, attr1); +#if defined(CPUARM) + v1_val = (uint8_t)cs->v1; +#endif + putsMixerSource(CSW_2ND_COLUMN, y, v1_val, attr1); if (horz == 1) { INCDEC_SET_FLAG(INCDEC_SOURCE); INCDEC_ENABLE_CHECK(isSourceAvailable); @@ -4623,11 +4626,11 @@ void menuModelLogicalSwitches(uint8_t event) INCDEC_ENABLE_CHECK(NULL); } #if defined(FRSKY) - if (v1_unsigned >= MIXSRC_FIRST_TELEM) { - putsTelemetryChannel(CSW_3RD_COLUMN, y, v1_unsigned - MIXSRC_FIRST_TELEM, convertCswTelemValue(cs), LEFT|attr2); - v2_max = maxTelemValue(v1_unsigned - MIXSRC_FIRST_TELEM + 1); + if (v1_val >= MIXSRC_FIRST_TELEM) { + putsTelemetryChannel(CSW_3RD_COLUMN, y, v1_val - MIXSRC_FIRST_TELEM, convertCswTelemValue(cs), LEFT|attr2); + v2_max = maxTelemValue(v1_val - MIXSRC_FIRST_TELEM + 1); #if defined(CPUARM) - v2_min = minTelemValue(v1_unsigned - MIXSRC_FIRST_TELEM + 1); + v2_min = minTelemValue(v1_val - MIXSRC_FIRST_TELEM + 1); if (cs->v2 < v2_min || cs->v2 > v2_max) { cs->v2 = 0; eeDirty(EE_MODEL); @@ -4652,8 +4655,8 @@ void menuModelLogicalSwitches(uint8_t event) v2_min = -125; v2_max = 125; } #else - if (v1_unsigned >= MIXSRC_FIRST_TELEM) { - putsTelemetryChannel(CSW_3RD_COLUMN, y, v1_unsigned - MIXSRC_FIRST_TELEM, convertCswTelemValue(cs), LEFT|attr2); + if (v1_val >= MIXSRC_FIRST_TELEM) { + putsTelemetryChannel(CSW_3RD_COLUMN, y, v1_val - MIXSRC_FIRST_TELEM, convertCswTelemValue(cs), LEFT|attr2); v2_min = -128; v2_max = 127; } else { @@ -4728,17 +4731,17 @@ void menuModelLogicalSwitches(uint8_t event) break; } case LS_FIELD_V1: - cs->v1 = CHECK_INCDEC_PARAM(event, v1_unsigned, v1_min, v1_max); + cs->v1 = CHECK_INCDEC_PARAM(event, v1_val, v1_min, v1_max); break; case LS_FIELD_V2: cs->v2 = CHECK_INCDEC_PARAM(event, cs->v2, v2_min, v2_max); #if defined(PCBTARANIS) - if (cstate==LS_FAMILY_OFS && v1_unsigned!=0 && event==EVT_KEY_LONG(KEY_ENTER)) { + if (cstate==LS_FAMILY_OFS && cs->v1!=0 && event==EVT_KEY_LONG(KEY_ENTER)) { killEvents(event); - getvalue_t x = getValue(v1_unsigned); - if (v1_unsigned < MIXSRC_GVAR1) + getvalue_t x = getValue(v1_val); + if (v1_val < MIXSRC_GVAR1) cs->v2 = calcRESXto100(x); - else if (v1_unsigned - MIXSRC_FIRST_TELEM + 1 == TELEM_ALT) + else if (v1_val - MIXSRC_FIRST_TELEM + 1 == TELEM_ALT) cs->v2 *= 100; eeDirty(EE_MODEL); } From 93b895a4f5999fe588f47edf8178e5142c583897 Mon Sep 17 00:00:00 2001 From: Bertrand Songis Date: Thu, 27 Feb 2014 17:45:37 +0100 Subject: [PATCH 88/89] Issue #628 fixed --- companion/src/eeprominterface.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/companion/src/eeprominterface.cpp b/companion/src/eeprominterface.cpp index bf1c91cdc..f72721f79 100644 --- a/companion/src/eeprominterface.cpp +++ b/companion/src/eeprominterface.cpp @@ -942,6 +942,7 @@ void ModelData::setDefault(uint8_t id) clear(); used = true; sprintf(name, "MODEL%02d", id+1); + modelId = id+1; } int ModelData::getTrimValue(int phaseIdx, int trimIdx) From 423d1a4437b64d3cc737ff71d12c1e4757eaffec Mon Sep 17 00:00:00 2001 From: Andre Bernet Date: Thu, 27 Feb 2014 22:22:34 +0100 Subject: [PATCH 89/89] French translations --- radio/src/translations/fr.h.txt | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/radio/src/translations/fr.h.txt b/radio/src/translations/fr.h.txt index 26d3593a9..b84a961d7 100644 --- a/radio/src/translations/fr.h.txt +++ b/radio/src/translations/fr.h.txt @@ -267,7 +267,7 @@ #define TR_RSSI_0 "Tx\0 " #define TR_RSSI_1 "Rx\0 " #endif -#define TR_VTELEMCHNS "---\0""Batt""Chr1""Chr2" TR_RSSI_0 TR_RSSI_1 "A1\0 ""A2\0 ""Alt\0""Rpm\0""Carb""T1\0 ""T2\0 ""Vit\0""Dist""AltG""Elem""Velm""Vfas""Cour""Cnsm""Puis""AccX""AccY""AccZ""Cap\0""VitV""ASpd""dTE\0""A1-\0""A2-\0""Alt-""Alt+""Rpm+""T1+\0""T2+\0""Vit+""Dst+""Cel-""Vfs-""Cur+""Pwr+""Acc\0""Time" +#define TR_VTELEMCHNS "---\0""Batt""Chr1""Chr2" TR_RSSI_0 TR_RSSI_1 "A1\0 ""A2\0 ""Alt\0""Rpm\0""Carb""T1\0 ""T2\0 ""Vit\0""Dist""AltG""Elem""Velm""Vfas""Cour""Cnsm""Puis""AccX""AccY""AccZ""Cap\0""VitV""VitA""dET\0""A1-\0""A2-\0""Alt-""Alt+""Rpm+""T1+\0""T2+\0""Vit+""Dst+""Elm-""Vfs-""Cur+""Pui+""Acc\0""Tmps" #if defined(CPUARM) #define LEN_VUNITSSYSTEM TR("\006", "\012") @@ -584,8 +584,8 @@ #define TR_MENUCURVES "COURBES" #define TR_MENUCURVE "COURBE" -#define TR_MENUCUSTOMSWITCH "INTER PERS." -#define TR_MENUCUSTOMSWITCHES "INTERS PERS." +#define TR_MENUCUSTOMSWITCH "INTER LOG." +#define TR_MENUCUSTOMSWITCHES TR("INTERS LOG.","INTERS LOGIQUES") #define TR_MENUCUSTOMFUNC TR("FONCTIONS SPEC.","FONCTIONS SPECIALES") #define TR_MENUTELEMETRY "TELEMESURE" #define TR_MENUTEMPLATES "GABARITS" @@ -661,7 +661,7 @@ #define TR_SD_SIZE "Taille:" #define TR_TYPE "Type" #define TR_GLOBAL_VARS "Variables Globales" -#define TR_GLOBAL_V "GLOBAL V." +#define TR_GLOBAL_V "V. GLOBALES" #define TR_GLOBAL_VAR "Variable globale" #define TR_MENUGLOBALVARS "VARIABLES GLOBALES" #define TR_OWN "Pers" @@ -753,7 +753,7 @@ #define TR_ABOUT_OPENTX_5 TR("bienvenues!","sont bienvenues!") #define TR_ABOUT_BERTRAND_1 "Bertrand Songis" -#define TR_ABOUT_BERTRAND_2 TR("Auteur\001principal\001d'openTx","Auteur principal d'openTx") +#define TR_ABOUT_BERTRAND_2 TR("Auteur\001principal\001d'OpenTX","Auteur principal d'OpenTX") #define TR_ABOUT_BERTRAND_3 TR("Codéveloppeur\001de\001C9X","Codéveloppeur de Companion9x") #define TR_ABOUT_MIKE_1 "Mike Blandford"