#include <SPI.h> // Needed for NRF24L01
#include <RF24.h> // Include the NRF24L01 library
#include <FastLED.h>
// NRF24L01 Configuration
#define NRF_CE_PIN 7
#define NRF_CSN_PIN 8
RF24 radio(NRF_CE_PIN, NRF_CSN_PIN); // CE, CSN
const byte address[6] = "00001"; // Must match the receiver's address
// --- Button Pins ---
const int stack_btn = A2;
const int launch_btn = 2;
const int down_btn = A1;
const int up_btn = A0;
const int openClose_btn = A3;
const int sideToSide_btn = A4;
const int shipQD_btn = A5;
const int arm_btn = 3;
int counter = 5;
// --- FastLED Configuration ---
#define LED_PIN 9
#define NUM_LEDS 10
#define BRIGHTNESS 100
#define LED_TYPE WS2812
#define COLOR_ORDER GRB
CRGB leds[NUM_LEDS];
// bool coloredPositions[NUM_LEDS]; // Not used in transmitter, can be removed
// CRGB coloredColors[NUM_LEDS]; // Not used in transmitter, can be removed
/* --- 7-Segment Display Pins ---
#define SEG_PIN_A 4
#define SEG_PIN_B 5
#define SEG_PIN_C 6
#define SEG_PIN_D 7
#define SEG_PIN_E 8
#define SEG_PIN_F 10
#define SEG_PIN_G 11
#define SEG_PIN_COM 2
#define SEG_PIN_D A7 // Example: Placeholder
#define SEG_PIN_E A7 // Example: Placeholder
#define SEG_PIN_F A7 // Example: Placeholder
#define SEG_PIN_G A7 // Example: Placeholder
//A7 is an INPUT ONLY pin on Uno/Nano, so it CANNOT drive segments.
*/
void setup() {
Serial.begin(9600);
while (!Serial && millis() < 5000); // Wait for serial connection
Serial.println("NRF24L01 Transmitter Starting...");
// Initialize NRF24L01 radio
if (!radio.begin()) {
Serial.println("Radio hardware not responding!");
//while (1) {} // Halt
}
radio.setPALevel(RF24_PA_LOW); // Set power amplifier level (MIN, LOW, HIGH, MAX)
radio.openWritingPipe(address); // Open a writing pipe to the receiver
radio.stopListening(); // We are transmitting, not receiving
Serial.print("Transmitting to address: ");
Serial.println((char*)address);
FastLED.addLeds<LED_TYPE, LED_PIN, COLOR_ORDER>(leds, NUM_LEDS).setCorrection(TypicalLEDStrip);
FastLED.setBrightness(BRIGHTNESS);
fill_solid(leds, NUM_LEDS, CRGB::Black);
FastLED.show();
pinMode(stack_btn, INPUT_PULLUP); // Using INPUT_PULLUP simplifies wiring (no external resistor needed)
pinMode(launch_btn, INPUT_PULLUP);
pinMode(down_btn, INPUT_PULLUP);
pinMode(up_btn, INPUT_PULLUP);
pinMode(openClose_btn, INPUT_PULLUP);
pinMode(sideToSide_btn, INPUT_PULLUP);
pinMode(shipQD_btn, INPUT_PULLUP);
pinMode(arm_btn, INPUT_PULLUP);
/*
pinMode(SEG_PIN_A, OUTPUT);
pinMode(SEG_PIN_B, OUTPUT);
pinMode(SEG_PIN_C, OUTPUT);
pinMode(SEG_PIN_D, OUTPUT);
pinMode(SEG_PIN_E, OUTPUT);
pinMode(SEG_PIN_F, OUTPUT);
pinMode(SEG_PIN_G, OUTPUT);
pinMode(SEG_PIN_COM, OUTPUT);
*/
Serial.println("Setup complete. Ready to transmit.");
}
void loop() {
// Check arm status for LED
if (digitalRead(arm_btn) == LOW) { // LOW because of INPUT_PULLUP
fill_solid(leds, NUM_LEDS, CRGB::Green);
FastLED.setBrightness(100);
} else {
fill_solid(leds, NUM_LEDS, CRGB::Black);
}
FastLED.show(); // Show LED status regardless of button presses
// Check buttons and send messages
if (digitalRead(stack_btn) == LOW) { // LOW because of INPUT_PULLUP
sendMessage("stack");
delay(200); // Debounce/prevent rapid fire
}
if (digitalRead(launch_btn) == LOW) {
if (digitalRead(arm_btn) == LOW) { // Check if armed
fill_solid(leds, NUM_LEDS, CRGB::Green); // Indicate armed launch
FastLED.setBrightness(255);
FastLED.show();
sendMessage("launch");
//countdown(); // Perform countdown
FastLED.setBrightness(BRIGHTNESS); // Reset brightness
fill_solid(leds, NUM_LEDS, CRGB::Green); // Back to armed green or black if disarmed
FastLED.show();
} else {
Serial.println("Launch attempted but NOT ARMED!");
fill_solid(leds, NUM_LEDS, CRGB::Red); // Indicate not armed
FastLED.setBrightness(100);
FastLED.show();
delay(1000);
fill_solid(leds, NUM_LEDS, CRGB::Black); // Clear red
FastLED.show();
}
delay(200); // Debounce
}
if (digitalRead(down_btn) == LOW) {
sendMessage("down");
delay(200);
}
if (digitalRead(up_btn) == LOW) {
sendMessage("up");
delay(200);
}
if (digitalRead(openClose_btn) == LOW) {
sendMessage("openClose");
delay(200);
}
if (digitalRead(sideToSide_btn) == LOW) {
sendMessage("sideToSide");
delay(200);
}
if (digitalRead(shipQD_btn) == LOW) {
sendMessage("shipQD");
delay(200);
}
}
void sendMessage(const char *message) {
Serial.print("Sending: ");
Serial.println(message);
// The NRF24L01 library handles C-strings well. Send length including null terminator.
if (radio.write(message, strlen(message) + 1)) {
// Serial.println(" ...Success"); // Optional: for debugging successful sends
} else {
//Serial.println(" ...Send failed");
}
}
/*void countdown() {
Serial.println("Countdown initiated...");
digitalWrite(SEG_PIN_COM, HIGH);
clearDisplay(); displayNum(5); delay(1000);
clearDisplay(); displayNum(4); delay(1000);
clearDisplay(); displayNum(3); delay(1000);
clearDisplay(); displayNum(2); delay(1000);
clearDisplay(); displayNum(1); delay(1000);
clearDisplay(); displayNum(0); delay(1000);
digitalWrite(SEG_PIN_COM, LOW); // Turn off display
clearDisplay(); // Ensure segments are off
}
// Helper to turn off all segments
void clearDisplay(void) {
digitalWrite(SEG_PIN_A, HIGH); // HIGH for common anode to turn OFF segment
digitalWrite(SEG_PIN_B, HIGH);
digitalWrite(SEG_PIN_C, HIGH);
digitalWrite(SEG_PIN_D, HIGH);
digitalWrite(SEG_PIN_E, HIGH);
digitalWrite(SEG_PIN_F, HIGH);
digitalWrite(SEG_PIN_G, HIGH);
}
// Display a single digit (0-9)
// Note: For common anode, LOW means segment ON, HIGH means segment OFF
void displayNum(int num) {
clearDisplay(); // Start with all segments off
switch (num) {
case 0:
digitalWrite(SEG_PIN_A, LOW); digitalWrite(SEG_PIN_B, LOW); digitalWrite(SEG_PIN_C, LOW);
digitalWrite(SEG_PIN_D, LOW); digitalWrite(SEG_PIN_E, LOW); digitalWrite(SEG_PIN_F, LOW);
break;
case 1:
digitalWrite(SEG_PIN_B, LOW); digitalWrite(SEG_PIN_C, LOW);
break;
case 2:
digitalWrite(SEG_PIN_A, LOW); digitalWrite(SEG_PIN_B, LOW); digitalWrite(SEG_PIN_G, LOW);
digitalWrite(SEG_PIN_E, LOW); digitalWrite(SEG_PIN_D, LOW);
break;
case 3:
digitalWrite(SEG_PIN_A, LOW); digitalWrite(SEG_PIN_B, LOW); digitalWrite(SEG_PIN_C, LOW);
digitalWrite(SEG_PIN_D, LOW); digitalWrite(SEG_PIN_G, LOW);
break;
case 4:
digitalWrite(SEG_PIN_F, LOW); digitalWrite(SEG_PIN_B, LOW); digitalWrite(SEG_PIN_G, LOW);
digitalWrite(SEG_PIN_C, LOW);
break;
case 5:
digitalWrite(SEG_PIN_A, LOW); digitalWrite(SEG_PIN_F, LOW); digitalWrite(SEG_PIN_G, LOW);
digitalWrite(SEG_PIN_C, LOW); digitalWrite(SEG_PIN_D, LOW);
break;
// Add cases for 6, 7, 8, 9 if needed
default: // If num is out of range, display blank or an error pattern
clearDisplay();
break;
}
}*/