mirror of
https://github.com/meshtastic/firmware.git
synced 2025-06-08 22:22:05 +00:00
Initial support for RadioMaster Bandit. (#4523)
* Initial support for RadioMaster Bandit. * Different lighting can be made for Button 1 & 2 on the Bandit. Changes to AmbientLighting will turn off af shutdown(). * Trunk * Trunk again.
This commit is contained in:
parent
9b2ef971c2
commit
de41a054b0
@ -34,6 +34,7 @@ default_envs = tbeam
|
|||||||
;default_envs = wio-e5
|
;default_envs = wio-e5
|
||||||
;default_envs = radiomaster_900_bandit_nano
|
;default_envs = radiomaster_900_bandit_nano
|
||||||
;default_envs = radiomaster_900_bandit_micro
|
;default_envs = radiomaster_900_bandit_micro
|
||||||
|
;default_envs = radiomaster_900_bandit
|
||||||
;default_envs = heltec_capsule_sensor_v3
|
;default_envs = heltec_capsule_sensor_v3
|
||||||
;default_envs = heltec_vision_master_t190
|
;default_envs = heltec_vision_master_t190
|
||||||
;default_envs = heltec_vision_master_e213
|
;default_envs = heltec_vision_master_e213
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
#include "Observer.h"
|
||||||
#include "configuration.h"
|
#include "configuration.h"
|
||||||
|
|
||||||
#ifdef HAS_NCP5623
|
#ifdef HAS_NCP5623
|
||||||
@ -22,10 +23,18 @@ class AmbientLightingThread : public concurrency::OSThread
|
|||||||
public:
|
public:
|
||||||
explicit AmbientLightingThread(ScanI2C::DeviceType type) : OSThread("AmbientLightingThread")
|
explicit AmbientLightingThread(ScanI2C::DeviceType type) : OSThread("AmbientLightingThread")
|
||||||
{
|
{
|
||||||
|
notifyDeepSleepObserver.observe(¬ifyDeepSleep); // Let us know when shutdown() is issued.
|
||||||
|
|
||||||
|
// Enables Ambient Lighting by default if conditions are meet.
|
||||||
|
#if defined(HAS_NCP5623) || defined(RGBLED_RED) || defined(HAS_NEOPIXEL) || defined(UNPHONE)
|
||||||
|
#ifdef ENABLE_AMBIENTLIGHTING
|
||||||
|
moduleConfig.ambient_lighting.led_state = true;
|
||||||
|
#endif
|
||||||
|
#endif
|
||||||
// Uncomment to test module
|
// Uncomment to test module
|
||||||
// moduleConfig.ambient_lighting.led_state = true;
|
// moduleConfig.ambient_lighting.led_state = true;
|
||||||
// moduleConfig.ambient_lighting.current = 10;
|
// moduleConfig.ambient_lighting.current = 10;
|
||||||
// // Default to a color based on our node number
|
// Default to a color based on our node number
|
||||||
// moduleConfig.ambient_lighting.red = (myNodeInfo.my_node_num & 0xFF0000) >> 16;
|
// moduleConfig.ambient_lighting.red = (myNodeInfo.my_node_num & 0xFF0000) >> 16;
|
||||||
// moduleConfig.ambient_lighting.green = (myNodeInfo.my_node_num & 0x00FF00) >> 8;
|
// moduleConfig.ambient_lighting.green = (myNodeInfo.my_node_num & 0x00FF00) >> 8;
|
||||||
// moduleConfig.ambient_lighting.blue = myNodeInfo.my_node_num & 0x0000FF;
|
// moduleConfig.ambient_lighting.blue = myNodeInfo.my_node_num & 0x0000FF;
|
||||||
@ -82,9 +91,46 @@ class AmbientLightingThread : public concurrency::OSThread
|
|||||||
return disable();
|
return disable();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// When shutdown() is issued, setLightingOff will be called.
|
||||||
|
CallbackObserver<AmbientLightingThread, void *> notifyDeepSleepObserver =
|
||||||
|
CallbackObserver<AmbientLightingThread, void *>(this, &AmbientLightingThread::setLightingOff);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
ScanI2C::DeviceType _type = ScanI2C::DeviceType::NONE;
|
ScanI2C::DeviceType _type = ScanI2C::DeviceType::NONE;
|
||||||
|
|
||||||
|
// Turn RGB lighting off, is used in junction to shutdown()
|
||||||
|
int setLightingOff(void *unused)
|
||||||
|
{
|
||||||
|
#ifdef HAS_NCP5623
|
||||||
|
rgb.setCurrent(0);
|
||||||
|
rgb.setRed(0);
|
||||||
|
rgb.setGreen(0);
|
||||||
|
rgb.setBlue(0);
|
||||||
|
LOG_INFO("Turn Off NCP5623 Ambient lighting.\n");
|
||||||
|
#endif
|
||||||
|
#ifdef HAS_NEOPIXEL
|
||||||
|
pixels.clear();
|
||||||
|
pixels.show();
|
||||||
|
LOG_INFO("Turn Off NeoPixel Ambient lighting.\n");
|
||||||
|
#endif
|
||||||
|
#ifdef RGBLED_CA
|
||||||
|
analogWrite(RGBLED_RED, 255 - 0);
|
||||||
|
analogWrite(RGBLED_GREEN, 255 - 0);
|
||||||
|
analogWrite(RGBLED_BLUE, 255 - 0);
|
||||||
|
LOG_INFO("Turn Off Ambient lighting RGB Common Anode.\n");
|
||||||
|
#elif defined(RGBLED_RED)
|
||||||
|
analogWrite(RGBLED_RED, 0);
|
||||||
|
analogWrite(RGBLED_GREEN, 0);
|
||||||
|
analogWrite(RGBLED_BLUE, 0);
|
||||||
|
LOG_INFO("Turn Off Ambient lighting RGB Common Cathode.\n");
|
||||||
|
#endif
|
||||||
|
#ifdef UNPHONE
|
||||||
|
unphone.rgb(0, 0, 0);
|
||||||
|
LOG_INFO("Turn Off unPhone Ambient lighting.\n");
|
||||||
|
#endif
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
void setLighting()
|
void setLighting()
|
||||||
{
|
{
|
||||||
#ifdef HAS_NCP5623
|
#ifdef HAS_NCP5623
|
||||||
@ -100,6 +146,17 @@ class AmbientLightingThread : public concurrency::OSThread
|
|||||||
pixels.fill(pixels.Color(moduleConfig.ambient_lighting.red, moduleConfig.ambient_lighting.green,
|
pixels.fill(pixels.Color(moduleConfig.ambient_lighting.red, moduleConfig.ambient_lighting.green,
|
||||||
moduleConfig.ambient_lighting.blue),
|
moduleConfig.ambient_lighting.blue),
|
||||||
0, NEOPIXEL_COUNT);
|
0, NEOPIXEL_COUNT);
|
||||||
|
|
||||||
|
// RadioMaster Bandit has addressable LED at the two buttons
|
||||||
|
// this allow us to set different lighting for them in variant.h file.
|
||||||
|
#ifdef RADIOMASTER_900_BANDIT
|
||||||
|
#if defined(BUTTON1_COLOR) && defined(BUTTON1_COLOR_INDEX)
|
||||||
|
pixels.fill(BUTTON1_COLOR, BUTTON1_COLOR_INDEX, 1);
|
||||||
|
#endif
|
||||||
|
#if defined(BUTTON2_COLOR) && defined(BUTTON2_COLOR_INDEX)
|
||||||
|
pixels.fill(BUTTON2_COLOR, BUTTON1_COLOR_INDEX, 1);
|
||||||
|
#endif
|
||||||
|
#endif
|
||||||
pixels.show();
|
pixels.show();
|
||||||
LOG_DEBUG("Initializing NeoPixel Ambient lighting w/ brightness(current)=%d, red=%d, green=%d, blue=%d\n",
|
LOG_DEBUG("Initializing NeoPixel Ambient lighting w/ brightness(current)=%d, red=%d, green=%d, blue=%d\n",
|
||||||
moduleConfig.ambient_lighting.current, moduleConfig.ambient_lighting.red, moduleConfig.ambient_lighting.green,
|
moduleConfig.ambient_lighting.current, moduleConfig.ambient_lighting.red, moduleConfig.ambient_lighting.green,
|
||||||
|
@ -16,7 +16,7 @@
|
|||||||
// In theory up to 27 dBm is possible, but the modules installed in most radios can cope with a max of 20. So BIG WARNING
|
// In theory up to 27 dBm is possible, but the modules installed in most radios can cope with a max of 20. So BIG WARNING
|
||||||
// if you set power to something higher than 17 or 20 you might fry your board.
|
// if you set power to something higher than 17 or 20 you might fry your board.
|
||||||
|
|
||||||
#ifdef RADIOMASTER_900_BANDIT_NANO
|
#if defined(RADIOMASTER_900_BANDIT_NANO) || defined(RADIOMASTER_900_BANDIT)
|
||||||
// Structure to hold DAC and DB values
|
// Structure to hold DAC and DB values
|
||||||
typedef struct {
|
typedef struct {
|
||||||
uint8_t dac;
|
uint8_t dac;
|
||||||
@ -40,12 +40,23 @@ DACDB getDACandDB(uint8_t dbm)
|
|||||||
static const struct {
|
static const struct {
|
||||||
uint8_t dbm;
|
uint8_t dbm;
|
||||||
DACDB values;
|
DACDB values;
|
||||||
} dbmToDACDB[] = {
|
}
|
||||||
|
#ifdef RADIOMASTER_900_BANDIT_NANO
|
||||||
|
dbmToDACDB[] = {
|
||||||
{20, {168, 2}}, // 100mW
|
{20, {168, 2}}, // 100mW
|
||||||
{24, {148, 6}}, // 250mW
|
{24, {148, 6}}, // 250mW
|
||||||
{27, {128, 9}}, // 500mW
|
{27, {128, 9}}, // 500mW
|
||||||
{30, {90, 12}} // 1000mW
|
{30, {90, 12}} // 1000mW
|
||||||
};
|
};
|
||||||
|
#endif
|
||||||
|
#ifdef RADIOMASTER_900_BANDIT
|
||||||
|
dbmToDACDB[] = {
|
||||||
|
{20, {165, 2}}, // 100mW
|
||||||
|
{24, {155, 6}}, // 250mW
|
||||||
|
{27, {142, 9}}, // 500mW
|
||||||
|
{30, {110, 10}} // 1000mW
|
||||||
|
};
|
||||||
|
#endif
|
||||||
const int numValues = sizeof(dbmToDACDB) / sizeof(dbmToDACDB[0]);
|
const int numValues = sizeof(dbmToDACDB) / sizeof(dbmToDACDB[0]);
|
||||||
|
|
||||||
// Find the interval dbm falls within and interpolate
|
// Find the interval dbm falls within and interpolate
|
||||||
@ -56,7 +67,12 @@ DACDB getDACandDB(uint8_t dbm)
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Return a default value if no match is found and default to 100mW
|
// Return a default value if no match is found and default to 100mW
|
||||||
|
#ifdef RADIOMASTER_900_BANDIT_NANO
|
||||||
DACDB defaultValue = {168, 2};
|
DACDB defaultValue = {168, 2};
|
||||||
|
#endif
|
||||||
|
#ifdef RADIOMASTER_900_BANDIT
|
||||||
|
DACDB defaultValue = {165, 2};
|
||||||
|
#endif
|
||||||
return defaultValue;
|
return defaultValue;
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
@ -95,7 +111,7 @@ bool RF95Interface::init()
|
|||||||
{
|
{
|
||||||
RadioLibInterface::init();
|
RadioLibInterface::init();
|
||||||
|
|
||||||
#ifdef RADIOMASTER_900_BANDIT_NANO
|
#if defined(RADIOMASTER_900_BANDIT_NANO) || defined(RADIOMASTER_900_BANDIT)
|
||||||
// DAC and DB values based on dBm using interpolation
|
// DAC and DB values based on dBm using interpolation
|
||||||
DACDB dacDbValues = getDACandDB(power);
|
DACDB dacDbValues = getDACandDB(power);
|
||||||
int8_t powerDAC = dacDbValues.dac;
|
int8_t powerDAC = dacDbValues.dac;
|
||||||
@ -117,7 +133,7 @@ bool RF95Interface::init()
|
|||||||
// enable PA
|
// enable PA
|
||||||
#ifdef RF95_PA_EN
|
#ifdef RF95_PA_EN
|
||||||
#if defined(RF95_PA_DAC_EN)
|
#if defined(RF95_PA_DAC_EN)
|
||||||
#ifdef RADIOMASTER_900_BANDIT_NANO
|
#if defined(RADIOMASTER_900_BANDIT_NANO) || defined(RADIOMASTER_900_BANDIT)
|
||||||
// Use calculated DAC value
|
// Use calculated DAC value
|
||||||
dacWrite(RF95_PA_EN, powerDAC);
|
dacWrite(RF95_PA_EN, powerDAC);
|
||||||
#else
|
#else
|
||||||
@ -163,7 +179,7 @@ bool RF95Interface::init()
|
|||||||
LOG_INFO("Frequency set to %f\n", getFreq());
|
LOG_INFO("Frequency set to %f\n", getFreq());
|
||||||
LOG_INFO("Bandwidth set to %f\n", bw);
|
LOG_INFO("Bandwidth set to %f\n", bw);
|
||||||
LOG_INFO("Power output set to %d\n", power);
|
LOG_INFO("Power output set to %d\n", power);
|
||||||
#ifdef RADIOMASTER_900_BANDIT_NANO
|
#if defined(RADIOMASTER_900_BANDIT_NANO) || defined(RADIOMASTER_900_BANDIT)
|
||||||
LOG_INFO("DAC output set to %d\n", powerDAC);
|
LOG_INFO("DAC output set to %d\n", powerDAC);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
@ -152,6 +152,8 @@
|
|||||||
#define HW_VENDOR meshtastic_HardwareModel_WIPHONE
|
#define HW_VENDOR meshtastic_HardwareModel_WIPHONE
|
||||||
#elif defined(RADIOMASTER_900_BANDIT_NANO)
|
#elif defined(RADIOMASTER_900_BANDIT_NANO)
|
||||||
#define HW_VENDOR meshtastic_HardwareModel_RADIOMASTER_900_BANDIT_NANO
|
#define HW_VENDOR meshtastic_HardwareModel_RADIOMASTER_900_BANDIT_NANO
|
||||||
|
#elif defined(RADIOMASTER_900_BANDIT)
|
||||||
|
#define HW_VENDOR meshtastic_HardwareModel_RADIOMASTER_900_BANDIT
|
||||||
#elif defined(HELTEC_CAPSULE_SENSOR_V3)
|
#elif defined(HELTEC_CAPSULE_SENSOR_V3)
|
||||||
#define HW_VENDOR meshtastic_HardwareModel_HELTEC_CAPSULE_SENSOR_V3
|
#define HW_VENDOR meshtastic_HardwareModel_HELTEC_CAPSULE_SENSOR_V3
|
||||||
#elif defined(HELTEC_VISION_MASTER_T190)
|
#elif defined(HELTEC_VISION_MASTER_T190)
|
||||||
|
14
variants/radiomaster_900_bandit/platformio.ini
Normal file
14
variants/radiomaster_900_bandit/platformio.ini
Normal file
@ -0,0 +1,14 @@
|
|||||||
|
[env:radiomaster_900_bandit]
|
||||||
|
extends = esp32_base
|
||||||
|
board = esp32doit-devkit-v1
|
||||||
|
build_flags =
|
||||||
|
${esp32_base.build_flags}
|
||||||
|
-DRADIOMASTER_900_BANDIT
|
||||||
|
-DVTABLES_IN_FLASH=1
|
||||||
|
-DCONFIG_DISABLE_HAL_LOCKS=1
|
||||||
|
-O2
|
||||||
|
-Ivariants/radiomaster_900_bandit
|
||||||
|
board_build.f_cpu = 240000000L
|
||||||
|
upload_protocol = esptool
|
||||||
|
lib_deps =
|
||||||
|
${esp32_base.lib_deps}
|
121
variants/radiomaster_900_bandit/variant.h
Normal file
121
variants/radiomaster_900_bandit/variant.h
Normal file
@ -0,0 +1,121 @@
|
|||||||
|
/*
|
||||||
|
Initial settings and work by https://github.com/gjelsoe
|
||||||
|
Unit provided by Radio Master RC
|
||||||
|
https://radiomasterrc.com/products/bandit-expresslrs-rf-module with 1.29" OLED display CH1115 driver
|
||||||
|
*/
|
||||||
|
|
||||||
|
/*
|
||||||
|
On this model then screen is NOT upside down, don't flip it for the user.
|
||||||
|
*/
|
||||||
|
#undef DISPLAY_FLIP_SCREEN
|
||||||
|
|
||||||
|
/*
|
||||||
|
I2C SDA and SCL.
|
||||||
|
0x18 - STK8XXX Accelerometer, Not supported yet.
|
||||||
|
0x3C - SH1115 Display Driver
|
||||||
|
*/
|
||||||
|
#define I2C_SDA 14
|
||||||
|
#define I2C_SCL 12
|
||||||
|
|
||||||
|
/*
|
||||||
|
No GPS - but free pins are available.
|
||||||
|
*/
|
||||||
|
#define HAS_GPS 0
|
||||||
|
#undef GPS_RX_PIN
|
||||||
|
#undef GPS_TX_PIN
|
||||||
|
|
||||||
|
/*
|
||||||
|
Pin connections from ESP32-D0WDQ6 to SX1276.
|
||||||
|
*/
|
||||||
|
#define LORA_DIO0 22
|
||||||
|
#define LORA_DIO1 21
|
||||||
|
#define LORA_SCK 18
|
||||||
|
#define LORA_MISO 19
|
||||||
|
#define LORA_MOSI 23
|
||||||
|
#define LORA_CS 4
|
||||||
|
#define LORA_RESET 5
|
||||||
|
#define LORA_TXEN 33
|
||||||
|
|
||||||
|
/*
|
||||||
|
This unit has a FAN built-in.
|
||||||
|
FAN is active at 250mW on it's ExpressLRS Firmware.
|
||||||
|
This FAN has TACHO signal on Pin 27 for use with PWM.
|
||||||
|
*/
|
||||||
|
#define RF95_FAN_EN 2
|
||||||
|
|
||||||
|
/*
|
||||||
|
LED PIN setup and it has a NeoPixel LED.
|
||||||
|
It's possible to setup colors for Button 1 and 2,
|
||||||
|
look at BUTTON1_COLOR, BUTTON1_COLOR_INDEX, BUTTON2_COLOR and BUTTON2_COLOR_INDEX
|
||||||
|
this is done here for now.
|
||||||
|
*/
|
||||||
|
#define HAS_NEOPIXEL // Enable the use of neopixels
|
||||||
|
#define NEOPIXEL_COUNT 6 // How many neopixels are connected
|
||||||
|
#define NEOPIXEL_DATA 15 // GPIO pin used to send data to the neopixels
|
||||||
|
#define NEOPIXEL_TYPE (NEO_GRB + NEO_KHZ800) // Type of neopixels in use
|
||||||
|
#define ENABLE_AMBIENTLIGHTING // Turn on Ambient Lighting
|
||||||
|
// #define BUTTON1_COLOR 0xFF0000 // Background light for Button 1 in HEX RGB Color (RadioMaster Bandit only).
|
||||||
|
// #define BUTTON1_COLOR_INDEX 0 // NeoPixel Index ID for Button 1
|
||||||
|
// #define BUTTON2_COLOR 0x0000FF // Background light for Button 2 in HEX RGB Color (RadioMaster Bandit only).
|
||||||
|
// #define BUTTON2_COLOR_INDEX 1 // NeoPixel Index ID for Button 2
|
||||||
|
|
||||||
|
/*
|
||||||
|
It has 1 x five-way and 2 x normal buttons.
|
||||||
|
|
||||||
|
Button GPIO RGB Index
|
||||||
|
---------------------------
|
||||||
|
Five-way 39 -
|
||||||
|
Button 1 34 0
|
||||||
|
Button 2 35 1
|
||||||
|
|
||||||
|
Five way button when using ADC.
|
||||||
|
2.632V, 2.177V, 1.598V, 1.055V, 0V
|
||||||
|
|
||||||
|
ADC Values:
|
||||||
|
{ UP, DOWN, LEFT, RIGHT, ENTER, IDLE }
|
||||||
|
3227, 0 ,1961, 2668, 1290, 4095
|
||||||
|
|
||||||
|
Five way button when using ADC.
|
||||||
|
https://github.com/ExpressLRS/targets/blob/f3215b5ec891108db1a13523e4163950cfcadaac/TX/Radiomaster%20Bandit.json#L41
|
||||||
|
|
||||||
|
*/
|
||||||
|
#define INPUTBROKER_EXPRESSLRSFIVEWAY_TYPE
|
||||||
|
#define PIN_JOYSTICK 39
|
||||||
|
#define JOYSTICK_ADC_VALS /*UP*/ 3227, /*DOWN*/ 0, /*LEFT*/ 1961, /*RIGHT*/ 2668, /*OK*/ 1290, /*IDLE*/ 4095
|
||||||
|
|
||||||
|
/*
|
||||||
|
Normal Button Pin setup.
|
||||||
|
*/
|
||||||
|
#define BUTTON_PIN 34
|
||||||
|
#define BUTTON_NEED_PULLUP
|
||||||
|
|
||||||
|
/*
|
||||||
|
No External notification.
|
||||||
|
*/
|
||||||
|
#undef EXT_NOTIFY_OUT
|
||||||
|
|
||||||
|
/*
|
||||||
|
Remapping PIN Names.
|
||||||
|
Note, that this unit uses RFO
|
||||||
|
*/
|
||||||
|
#define USE_RF95
|
||||||
|
#define USE_RF95_RFO
|
||||||
|
#define RF95_CS LORA_CS
|
||||||
|
#define RF95_DIO1 LORA_DIO1
|
||||||
|
#define RF95_TXEN LORA_TXEN
|
||||||
|
#define RF95_RESET LORA_RESET
|
||||||
|
#define RF95_MAX_POWER 10
|
||||||
|
|
||||||
|
/*
|
||||||
|
This module has Skyworks SKY66122 controlled by dacWrite
|
||||||
|
power ranging from 100mW to 1000mW.
|
||||||
|
|
||||||
|
Mapping of PA_LEVEL to Power output: GPIO26/dacWrite
|
||||||
|
168 -> 100mW
|
||||||
|
155 -> 250mW
|
||||||
|
142 -> 500mW
|
||||||
|
110 -> 1000mW
|
||||||
|
*/
|
||||||
|
#define RF95_PA_EN 26
|
||||||
|
#define RF95_PA_DAC_EN
|
||||||
|
#define RF95_PA_LEVEL 110
|
Loading…
Reference in New Issue
Block a user